Using boost now

This commit is contained in:
Artur K 2012-03-15 18:55:27 +01:00
parent a740690e04
commit 4dd97b0709
16 changed files with 553 additions and 437 deletions

View File

@ -5,6 +5,8 @@
#include <string> #include <string>
#include <llvm/ADT/ilist.h> #include <llvm/ADT/ilist.h>
#include <llvm/ADT/ilist_node.h> #include <llvm/ADT/ilist_node.h>
#include <boost/range.hpp>
#include "icode.h"
#include "types.h" #include "types.h"
#include "graph.h" #include "graph.h"
//#include "icode.h" //#include "icode.h"
@ -12,22 +14,21 @@
struct Function; struct Function;
class CIcodeRec; class CIcodeRec;
struct BB; struct BB;
struct LOCAL_ID;
struct interval; struct interval;
struct ICODE;
typedef std::list<ICODE>::iterator iICODE; struct TYPEADR_TYPE
typedef std::list<ICODE>::reverse_iterator riICODE;
typedef union
{ {
uint32_t ip; /* Out edge icode address */ uint32_t ip; /* Out edge icode address */
BB * BBptr; /* Out edge pointer to next BB */ BB * BBptr; /* Out edge pointer to next BB */
interval *intPtr; /* Out edge ptr to next interval*/ interval *intPtr; /* Out edge ptr to next interval*/
} TYPEADR_TYPE; };
struct BB : public llvm::ilist_node<BB> struct BB : public llvm::ilist_node<BB>
{ {
private: private:
BB(const BB&); BB(const BB&);
BB() : nodeType(0),traversed(0), BB() : nodeType(0),traversed(DFS_NONE),
numHlIcodes(0),flg(0), numHlIcodes(0),flg(0),
inEdges(0), inEdges(0),
edges(0),beenOnH(0),inEdgeCount(0),reachingInt(0), edges(0),beenOnH(0),inEdgeCount(0),reachingInt(0),
@ -38,10 +39,14 @@ private:
} }
//friend class SymbolTableListTraits<BB, Function>; //friend class SymbolTableListTraits<BB, Function>;
iICODE range_start; typedef boost::iterator_range<iICODE> rCODE;
iICODE range_end; rCODE instructions;
public: public:
struct ValidFunctor
{
bool operator()(BB *p) {return p->valid();}
};
iICODE begin(); iICODE begin();
iICODE end() const; iICODE end() const;
riICODE rbegin(); riICODE rbegin();
@ -50,7 +55,7 @@ public:
ICODE &back(); ICODE &back();
size_t size(); size_t size();
uint8_t nodeType; /* Type of node */ uint8_t nodeType; /* Type of node */
int traversed; /* Boolean: traversed yet? */ eDFS traversed; /* last traversal id is held here traversed yet? */
int numHlIcodes; /* No. of high-level icodes */ int numHlIcodes; /* No. of high-level icodes */
uint32_t flg; /* BB flags */ uint32_t flg; /* BB flags */
@ -94,8 +99,9 @@ public:
int caseTail; /* tail node for the case */ int caseTail; /* tail node for the case */
int index; /* Index, used in several ways */ int index; /* Index, used in several ways */
static BB * Create(void *ctx=0,const std::string &s="",Function *parent=0,BB *insertBefore=0); static BB * Create(void *ctx=0,const std::string &s="",Function *parent=0,BB *insertBefore=0);
static BB * Create(int start, int ip, uint8_t nodeType, int numOutEdges, Function * parent); static BB * Create(int start, int ip, uint8_t nodeType, int numOutEdges, Function * parent);
static BB * Create(iICODE start, iICODE fin, uint8_t _nodeType, int numOutEdges, Function *parent);
void writeCode(int indLevel, Function *pProc, int *numLoc, int latchNode, int ifFollow); void writeCode(int indLevel, Function *pProc, int *numLoc, int latchNode, int ifFollow);
void mergeFallThrough(CIcodeRec &Icode); void mergeFallThrough(CIcodeRec &Icode);
void dfsNumbering(std::vector<BB *> &dfsLast, int *first, int *last); void dfsNumbering(std::vector<BB *> &dfsLast, int *first, int *last);
@ -105,10 +111,19 @@ static BB * Create(int start, int ip, uint8_t nodeType, int numOutEdges, Functio
/// ///
const Function *getParent() const { return Parent; } const Function *getParent() const { return Parent; }
Function *getParent() { return Parent; } Function *getParent() { return Parent; }
void writeBB(std::ostream &ostr, int lev, Function *pProc, int *numLoc); void writeBB(std::ostream &ostr, int lev, Function *pProc, int *numLoc);
BB *rmJMP(int marker, BB *pBB); BB * rmJMP(int marker, BB *pBB);
void genDU1(); void genDU1();
int findBBExps(LOCAL_ID &locals, Function *f);
bool valid() {return 0==(flg & INVALID_BB); }
bool wasTraversedAtLevel(int l) const {return traversed==l;}
ICODE * writeLoopHeader(int &indLevel, Function* pProc, int *numLoc, BB *&latch, boolT &repCond);
void addOutEdge(uint32_t ip) // TODO: fix this
{
edges[0].ip = ip;
}
private: private:
bool isEndOfPath(int latch_node_idx) const;
Function *Parent; Function *Parent;
}; };

View File

@ -124,6 +124,9 @@ public:
r->name = nm; r->name = nm;
return r; return r;
} }
bool anyFlagsSet(uint32_t t) { return (flg&t)!=0;}
bool hasRegArgs() const { return (flg & REG_ARGS)!=0;}
bool isLibrary() const { return (flg & PROC_ISLIB)!=0;}
void compoundCond(); void compoundCond();
void writeProcComments(); void writeProcComments();
void lowLevelAnalysis(); void lowLevelAnalysis();
@ -140,10 +143,8 @@ public:
void process_operands(ICODE &pIcode, STATE *pstate); void process_operands(ICODE &pIcode, STATE *pstate);
boolT process_JMP(ICODE &pIcode, STATE *pstate, CALL_GRAPH *pcallGraph); boolT process_JMP(ICODE &pIcode, STATE *pstate, CALL_GRAPH *pcallGraph);
boolT process_CALL(ICODE &pIcode, CALL_GRAPH *pcallGraph, STATE *pstate); boolT process_CALL(ICODE &pIcode, CALL_GRAPH *pcallGraph, STATE *pstate);
void displayCFG();
void freeCFG(); void freeCFG();
void codeGen(std::ostream &fs); void codeGen(std::ostream &fs);
void displayStats();
void mergeFallThrough(BB *pBB); void mergeFallThrough(BB *pBB);
void structIfs(); void structIfs();
void structLoops(derSeq *derivedG); void structLoops(derSeq *derivedG);
@ -151,20 +152,25 @@ public:
void controlFlowAnalysis(); void controlFlowAnalysis();
void newRegArg(iICODE picode, iICODE ticode); void newRegArg(iICODE picode, iICODE ticode);
void writeProcComments(std::ostream &ostr); void writeProcComments(std::ostream &ostr);
void displayCFG();
void displayStats();
void processHliCall(COND_EXPR *exp, iICODE picode);
protected:
bool removeInEdge_Flag_and_ProcessLatch(BB *pbb, BB *a, BB *b);
bool Case_X_and_Y(BB* pbb, BB* thenBB, BB* elseBB); bool Case_X_and_Y(BB* pbb, BB* thenBB, BB* elseBB);
bool Case_X_or_Y(BB* pbb, BB* thenBB, BB* elseBB); bool Case_X_or_Y(BB* pbb, BB* thenBB, BB* elseBB);
bool Case_notX_or_Y(BB* pbb, BB* thenBB, BB* elseBB); bool Case_notX_or_Y(BB* pbb, BB* thenBB, BB* elseBB);
bool Case_notX_and_Y(BB* pbb, BB* thenBB, BB* elseBB); bool Case_notX_and_Y(BB* pbb, BB* thenBB, BB* elseBB);
void replaceInEdge(BB* where, BB* which, BB* with); void replaceInEdge(BB* where, BB* which, BB* with);
protected: void processExpPush(int &numHlIcodes, iICODE picode);
bool removeInEdge_Flag_and_ProcessLatch(BB *pbb, BB *a, BB *b);
// TODO: replace those with friend visitor ? // TODO: replace those with friend visitor ?
void propLongReg(int loc_ident_idx, const ID &pLocId); void propLongReg(int loc_ident_idx, const ID &pLocId);
void propLongStk(int i, const ID &pLocId); void propLongStk(int i, const ID &pLocId);
void propLongGlb(int i, const ID &pLocId); void propLongGlb(int i, const ID &pLocId);
void processTargetIcode(iICODE picode, int &numHlIcodes, iICODE ticode, bool isLong); void processTargetIcode(iICODE picode, int &numHlIcodes, iICODE ticode, bool isLong);
void processHliCall(COND_EXPR *exp, iICODE picode);
int findBackwarLongDefs(int loc_ident_idx, const ID &pLocId, iICODE iter); int findBackwarLongDefs(int loc_ident_idx, const ID &pLocId, iICODE iter);
int findForwardLongUses(int loc_ident_idx, const ID &pLocId, iICODE beg); int findForwardLongUses(int loc_ident_idx, const ID &pLocId, iICODE beg);
@ -176,6 +182,6 @@ public:
void findIdioms(); void findIdioms();
void propLong(); void propLong();
void genLiveKtes(); void genLiveKtes();
uint8_t findDerivedSeq (derSeq &derivedGi); uint8_t findDerivedSeq (derSeq &derivedGi);
bool nextOrderGraph(derSeq &derivedGi); bool nextOrderGraph(derSeq &derivedGi);
}; };

View File

@ -85,7 +85,7 @@ public:
static COND_EXPR * id(const LLInst &ll_insn, opLoc sd, Function *pProc, iICODE ix_, ICODE &duIcode, operDu du); static COND_EXPR * id(const LLInst &ll_insn, opLoc sd, Function *pProc, iICODE ix_, ICODE &duIcode, operDu du);
static COND_EXPR *boolOp(COND_EXPR *_lhs, COND_EXPR *_rhs, condOp _op); static COND_EXPR *boolOp(COND_EXPR *_lhs, COND_EXPR *_rhs, condOp _op);
static bool insertSubTreeLongReg(COND_EXPR *exp, COND_EXPR **tree, int longIdx); static bool insertSubTreeLongReg(COND_EXPR *exp, COND_EXPR **tree, int longIdx);
static bool insertSubTreeReg(COND_EXPR *&tree, COND_EXPR *_expr, eReg regi, LOCAL_ID *locsym); static bool insertSubTreeReg(COND_EXPR *&tree, COND_EXPR *_expr, eReg regi, const LOCAL_ID *locsym);
public: public:
virtual COND_EXPR *clone() const; virtual COND_EXPR *clone() const;
void release(); void release();
@ -105,8 +105,8 @@ public:
virtual ~COND_EXPR() {} virtual ~COND_EXPR() {}
public: public:
virtual COND_EXPR *inverse() const; // return new COND_EXPR that is invarse of this virtual COND_EXPR *inverse() const; // return new COND_EXPR that is invarse of this
virtual bool xClear(iICODE f, iICODE t, iICODE lastBBinst, Function *pproc); virtual bool xClear(iICODE f, iICODE t, iICODE lastBBinst, const LOCAL_ID &locId);
virtual COND_EXPR *insertSubTreeReg(COND_EXPR *_expr, eReg regi, LOCAL_ID *locsym); virtual COND_EXPR *insertSubTreeReg(COND_EXPR *_expr, eReg regi, const LOCAL_ID *locsym);
virtual COND_EXPR *insertSubTreeLongReg(COND_EXPR *_expr, int longIdx); virtual COND_EXPR *insertSubTreeLongReg(COND_EXPR *_expr, int longIdx);
virtual hlType expType(Function *pproc) const; virtual hlType expType(Function *pproc) const;
}; };
@ -124,7 +124,7 @@ struct BinaryOperator : public COND_EXPR
static BinaryOperator *CreateAdd(COND_EXPR *l,COND_EXPR *r); static BinaryOperator *CreateAdd(COND_EXPR *l,COND_EXPR *r);
virtual COND_EXPR *inverse(); virtual COND_EXPR *inverse();
virtual COND_EXPR *clone(); virtual COND_EXPR *clone();
virtual bool xClear(iICODE f, iICODE t, iICODE lastBBinst, Function *pproc); virtual bool xClear(iICODE f, iICODE t, iICODE lastBBinst, const LOCAL_ID &locs);
virtual COND_EXPR *insertSubTreeReg(COND_EXPR *_expr, eReg regi, LOCAL_ID *locsym); virtual COND_EXPR *insertSubTreeReg(COND_EXPR *_expr, eReg regi, LOCAL_ID *locsym);
virtual COND_EXPR *insertSubTreeLongReg(COND_EXPR *_expr, int longIdx); virtual COND_EXPR *insertSubTreeLongReg(COND_EXPR *_expr, int longIdx);
@ -158,7 +158,7 @@ struct UnaryOperator : public COND_EXPR
COND_EXPR *unaryExp; COND_EXPR *unaryExp;
virtual COND_EXPR *inverse(); virtual COND_EXPR *inverse();
virtual COND_EXPR *clone(); virtual COND_EXPR *clone();
virtual bool xClear(iICODE f, iICODE t, iICODE lastBBinst, Function *pproc); virtual bool xClear(iICODE f, iICODE t, iICODE lastBBinst, const LOCAL_ID &locs);
static UnaryOperator *Create(condNodeType t, COND_EXPR *sub_expr) static UnaryOperator *Create(condNodeType t, COND_EXPR *sub_expr)
{ {
UnaryOperator *newExp = new UnaryOperator(); UnaryOperator *newExp = new UnaryOperator();

View File

@ -30,6 +30,7 @@ public:
} }
strTable decl; /* Declarations */ strTable decl; /* Declarations */
strTable code; /* C code */ strTable code; /* C code */
int current_indent;
}; };

View File

@ -28,6 +28,7 @@ enum eBBKind
/* Depth-first traversal constants */ /* Depth-first traversal constants */
enum eDFS enum eDFS
{ {
DFS_NONE,
DFS_DISP=1, /* Display graph pass */ DFS_DISP=1, /* Display graph pass */
DFS_MERGE=2, /* Merge nodes pass */ DFS_MERGE=2, /* Merge nodes pass */
DFS_NUM=3, /* DFS numbering pass */ DFS_NUM=3, /* DFS numbering pass */

View File

@ -13,6 +13,7 @@
#include <llvm/MC/MCInst.h> #include <llvm/MC/MCInst.h>
#include <llvm/MC/MCAsmInfo.h> #include <llvm/MC/MCAsmInfo.h>
#include <llvm/Value.h> #include <llvm/Value.h>
#include <boost/range.hpp>
#include "Enums.h" #include "Enums.h"
#include "state.h" // State depends on INDEXBASE, but later need STATE #include "state.h" // State depends on INDEXBASE, but later need STATE
//enum condId; //enum condId;
@ -26,6 +27,7 @@ struct ICODE;
struct bundle; struct bundle;
typedef std::list<ICODE>::iterator iICODE; typedef std::list<ICODE>::iterator iICODE;
typedef std::list<ICODE>::reverse_iterator riICODE; typedef std::list<ICODE>::reverse_iterator riICODE;
typedef boost::iterator_range<iICODE> rCODE;
/* uint8_t and uint16_t registers */ /* uint8_t and uint16_t registers */
@ -58,6 +60,7 @@ struct CallType : public HlTypeSupport
void allocStkArgs (int num); void allocStkArgs (int num);
bool newStkArg(COND_EXPR *exp, llIcode opcode, Function *pproc); bool newStkArg(COND_EXPR *exp, llIcode opcode, Function *pproc);
void placeStkArg(COND_EXPR *exp, int pos); void placeStkArg(COND_EXPR *exp, int pos);
virtual COND_EXPR * toId();
public: public:
bool removeRegFromLong(eReg regi, LOCAL_ID *locId) bool removeRegFromLong(eReg regi, LOCAL_ID *locId)
{ {
@ -285,6 +288,18 @@ protected:
HLTYPE m_hl; HLTYPE m_hl;
bool invalid; /* Has no HIGH_LEVEL equivalent */ bool invalid; /* Has no HIGH_LEVEL equivalent */
public: public:
template<int FLAG>
struct FlagFilter
{
bool operator()(ICODE *ic) {return ic->ll()->testFlags(FLAG);}
bool operator()(ICODE &ic) {return ic.ll()->testFlags(FLAG);}
};
template<int TYPE>
struct TypeFilter
{
bool operator()(ICODE *ic) {return ic->type==HIGH_LEVEL;}
bool operator()(ICODE &ic) {return ic.type==HIGH_LEVEL;}
};
/* Def/Use of registers and stack variables */ /* Def/Use of registers and stack variables */
struct DU_ICODE struct DU_ICODE
{ {
@ -399,6 +414,7 @@ public:
ICODE * addIcode(ICODE *pIcode); ICODE * addIcode(ICODE *pIcode);
void SetInBB(int start, int end, BB* pnewBB); void SetInBB(int start, int end, BB* pnewBB);
void SetInBB(rCODE &rang, BB* pnewBB);
bool labelSrch(uint32_t target, uint32_t &pIndex); bool labelSrch(uint32_t target, uint32_t &pIndex);
iterator labelSrch(uint32_t target); iterator labelSrch(uint32_t target);
ICODE * GetIcode(int ip); ICODE * GetIcode(int ip);

View File

@ -18,6 +18,7 @@
/* Type definition */ /* Type definition */
// this array has to stay in-order of addition i.e. not std::set<iICODE,std::less<iICODE> > // this array has to stay in-order of addition i.e. not std::set<iICODE,std::less<iICODE> >
// TODO: why ? // TODO: why ?
struct COND_EXPR;
struct ICODE; struct ICODE;
typedef std::list<ICODE>::iterator iICODE; typedef std::list<ICODE>::iterator iICODE;
struct IDX_ARRAY : public std::vector<iICODE> struct IDX_ARRAY : public std::vector<iICODE>
@ -104,6 +105,10 @@ struct ID
struct LOCAL_ID struct LOCAL_ID
{ {
std::vector<ID> id_arr; std::vector<ID> id_arr;
protected:
int newLongIdx(int16_t seg, int16_t offH, int16_t offL, uint8_t regi, hlType t);
int newLongGlb(int16_t seg, int16_t offH, int16_t offL, hlType t);
int newLongStk(hlType t, int offH, int offL);
public: public:
LOCAL_ID() LOCAL_ID()
{ {
@ -122,10 +127,10 @@ public:
void flagByteWordId(int off); void flagByteWordId(int off);
void propLongId(uint8_t regL, uint8_t regH, const char *name); void propLongId(uint8_t regL, uint8_t regH, const char *name);
size_t csym() const {return id_arr.size();} size_t csym() const {return id_arr.size();}
protected: void newRegArg(iICODE picode, iICODE ticode) const;
int newLongIdx(int16_t seg, int16_t offH, int16_t offL, uint8_t regi, hlType t); void processTargetIcode(iICODE picode, int &numHlIcodes, iICODE ticode, bool isLong) const;
int newLongGlb(int16_t seg, int16_t offH, int16_t offL, hlType t); void forwardSubs(COND_EXPR *lhs, COND_EXPR *rhs, iICODE picode, iICODE ticode, int &numHlIcodes) const;
int newLongStk(hlType t, int offH, int offL); COND_EXPR *createId(const ID *retVal, iICODE ix_);
}; };

View File

@ -50,7 +50,7 @@ struct STKSYM : public SymbolCommon
void setArgName(int i) void setArgName(int i)
{ {
char buf[32]; char buf[32];
sprintf (buf, "arg%ld", i); sprintf (buf, "arg%d", i);
name = buf; name = buf;
} }
}; };

View File

@ -1,10 +1,13 @@
#include <cassert> #include <cassert>
#include <string> #include <string>
#include <boost/range/rbegin.hpp>
#include <boost/range/rend.hpp>
#include <boost/range/adaptors.hpp>
#include "BasicBlock.h" #include "BasicBlock.h"
#include "Procedure.h" #include "Procedure.h"
#include "dcc.h" #include "dcc.h"
using namespace std; using namespace std;
using namespace boost;
BB *BB::Create(void *ctx, const string &s, Function *parent, BB *insertBefore) BB *BB::Create(void *ctx, const string &s, Function *parent, BB *insertBefore)
{ {
@ -12,29 +15,27 @@ BB *BB::Create(void *ctx, const string &s, Function *parent, BB *insertBefore)
pnewBB->Parent = parent; pnewBB->Parent = parent;
return pnewBB; return pnewBB;
} }
/**
BB *BB::Create(int start, int ip, uint8_t _nodeType, int numOutEdges, Function *parent) * @arg start - basic block starts here, might be parent->Icode.end()
* @arg fin - last of basic block's instructions
*/
BB *BB::Create(iICODE start, iICODE fin, uint8_t _nodeType, int numOutEdges, Function *parent)
{ {
BB* pnewBB; BB* pnewBB;
pnewBB = new BB; pnewBB = new BB;
pnewBB->nodeType = _nodeType; /* Initialise */ pnewBB->nodeType = _nodeType; /* Initialise */
pnewBB->immedDom = NO_DOM; pnewBB->immedDom = NO_DOM;
pnewBB->loopHead = pnewBB->caseHead = pnewBB->caseTail = pnewBB->loopHead = pnewBB->caseHead = pnewBB->caseTail =
pnewBB->latchNode= pnewBB->loopFollow = NO_NODE; pnewBB->latchNode= pnewBB->loopFollow = NO_NODE;
pnewBB->range_start = parent->Icode.begin(); pnewBB->instructions = make_iterator_range(start,fin);
pnewBB->range_end = parent->Icode.begin(); if(start==parent->Icode.end())
if(start!=-1)
{ {
advance(pnewBB->range_start,start); pnewBB->instructions = make_iterator_range(parent->Icode.end(),parent->Icode.end());
advance(pnewBB->range_end,ip+1);
} }
else else
{ {
pnewBB->range_end = parent->Icode.end(); pnewBB->instructions.advance_end(1); // 1 after fin, to create range where fin is inclusive
pnewBB->range_end = parent->Icode.end();
} }
if (numOutEdges) if (numOutEdges)
pnewBB->edges.resize(numOutEdges); pnewBB->edges.resize(numOutEdges);
@ -42,16 +43,32 @@ BB *BB::Create(int start, int ip, uint8_t _nodeType, int numOutEdges, Function *
* real code basic blocks (ie. not interval bbs) */ * real code basic blocks (ie. not interval bbs) */
if(parent) if(parent)
{ {
if (start >= 0) if (start != parent->Icode.end())
parent->Icode.SetInBB(start, ip, pnewBB); parent->Icode.SetInBB(pnewBB->instructions, pnewBB);
parent->heldBBs.push_back(pnewBB); parent->heldBBs.push_back(pnewBB);
parent->m_cfg.push_back(pnewBB); parent->m_cfg.push_back(pnewBB);
pnewBB->Parent = parent; pnewBB->Parent = parent;
} }
if (start != -1) /* Only for code BB's */ if ( start != parent->Icode.end() ) /* Only for code BB's */
stats.numBBbef++; stats.numBBbef++;
return pnewBB; return pnewBB;
} }
BB *BB::Create(int start, int ip, uint8_t _nodeType, int numOutEdges, Function *parent)
{
iICODE st(parent->Icode.begin());
iICODE fin(parent->Icode.begin());
if(start==-1)
{
st = parent->Icode.end();
fin = parent->Icode.end();
}
else
{
advance(st,start);
advance(fin,ip);
}
return Create(st,fin,_nodeType,numOutEdges,parent);
}
static const char *const s_nodeType[] = {"branch", "if", "case", "fall", "return", "call", static const char *const s_nodeType[] = {"branch", "if", "case", "fall", "return", "call",
"loop", "repeat", "interval", "cycleHead", "loop", "repeat", "interval", "cycleHead",
@ -67,7 +84,12 @@ void BB::display()
printf("start = %ld, length = %ld, #out edges = %ld\n", begin()->loc_ip, size(), edges.size()); printf("start = %ld, length = %ld, #out edges = %ld\n", begin()->loc_ip, size(), edges.size());
for (size_t i = 0; i < edges.size(); i++) for (size_t i = 0; i < edges.size(); i++)
printf(" outEdge[%2d] = %ld\n",i, edges[i].BBptr->begin()->loc_ip); {
if(edges[i].BBptr==0)
printf(" outEdge[%2d] = Unlinked out edge to %d\n",i, edges[i].ip);
else
printf(" outEdge[%2d] = %d\n",i, edges[i].BBptr->begin()->loc_ip);
}
} }
/***************************************************************************** /*****************************************************************************
* displayDfs - Displays the CFG using a depth first traversal * displayDfs - Displays the CFG using a depth first traversal
@ -131,11 +153,63 @@ void BB::displayDfs()
* current procedure. * current procedure.
* indLevel: indentation level - used for formatting. * indLevel: indentation level - used for formatting.
* numLoc: last # assigned to local variables */ * numLoc: last # assigned to local variables */
ICODE* BB::writeLoopHeader(int &indLevel, Function* pProc, int *numLoc, BB *&latch, boolT &repCond)
{
latch = pProc->m_dfsLast[this->latchNode];
std::ostringstream ostr;
ICODE* picode;
switch (loopType)
{
case WHILE_TYPE:
picode = &this->back();
/* Check for error in while condition */
if (picode->hl()->opcode != HLI_JCOND)
reportError (WHILE_FAIL);
/* Check if condition is more than 1 HL instruction */
if (numHlIcodes > 1)
{
/* Write the code for this basic block */
writeBB(ostr,indLevel, pProc, numLoc);
repCond = true;
}
/* Condition needs to be inverted if the loop body is along
* the THEN path of the header node */
if (edges[ELSE].BBptr->dfsLastNum == loopFollow)
{
picode->hl()->replaceExpr(picode->hl()->expr()->inverse());
}
{
string e=walkCondExpr (picode->hl()->expr(), pProc, numLoc);
ostr << "\n"<<indentStr(indLevel)<<"while ("<<e<<") {\n";
}
picode->invalidate();
break;
case REPEAT_TYPE:
ostr << "\n"<<indentStr(indLevel)<<"do {\n";
picode = &latch->back();
picode->invalidate();
break;
case ENDLESS_TYPE:
ostr << "\n"<<indentStr(indLevel)<<"for (;;) {\n";
}
cCode.appendCode(ostr.str());
stats.numHLIcode += 1;
indLevel++;
return picode;
}
bool BB::isEndOfPath(int latch_node_idx) const
{
return nodeType == RETURN_NODE || nodeType == TERMINATE_NODE ||
nodeType == NOWHERE_NODE || (dfsLastNum == latch_node_idx);
}
void BB::writeCode (int indLevel, Function * pProc , int *numLoc,int _latchNode, int _ifFollow) void BB::writeCode (int indLevel, Function * pProc , int *numLoc,int _latchNode, int _ifFollow)
{ {
int follow, /* ifFollow */ int follow; /* ifFollow */
_loopType, /* Type of loop, if any */
_nodeType; /* Type of node */
BB * succ, *latch; /* Successor and latching node */ BB * succ, *latch; /* Successor and latching node */
ICODE * picode; /* Pointer to HLI_JCOND instruction */ ICODE * picode; /* Pointer to HLI_JCOND instruction */
char *l; /* Pointer to HLI_JCOND expression */ char *l; /* Pointer to HLI_JCOND expression */
@ -146,60 +220,16 @@ void BB::writeCode (int indLevel, Function * pProc , int *numLoc,int _latchNode,
if ((_ifFollow != UN_INIT) && (this == pProc->m_dfsLast[_ifFollow])) if ((_ifFollow != UN_INIT) && (this == pProc->m_dfsLast[_ifFollow]))
return; return;
if (traversed == DFS_ALPHA) if (wasTraversedAtLevel(DFS_ALPHA))
return; return;
traversed = DFS_ALPHA; traversed = DFS_ALPHA;
/* Check for start of loop */ /* Check for start of loop */
repCond = false; repCond = false;
latch = NULL; latch = NULL;
_loopType = loopType; if (loopType)
if (_loopType)
{ {
latch = pProc->m_dfsLast[this->latchNode]; picode=writeLoopHeader(indLevel, pProc, numLoc, latch, repCond);
std::ostringstream ostr;
switch (_loopType)
{
case WHILE_TYPE:
picode = &this->back();
/* Check for error in while condition */
if (picode->hl()->opcode != HLI_JCOND)
reportError (WHILE_FAIL);
/* Check if condition is more than 1 HL instruction */
if (numHlIcodes > 1)
{
/* Write the code for this basic block */
writeBB(ostr,indLevel, pProc, numLoc);
repCond = true;
}
/* Condition needs to be inverted if the loop body is along
* the THEN path of the header node */
if (edges[ELSE].BBptr->dfsLastNum == loopFollow)
{
picode->hl()->replaceExpr(picode->hl()->expr()->inverse());
}
{
string e=walkCondExpr (picode->hl()->expr(), pProc, numLoc);
ostr << "\n"<<indentStr(indLevel)<<"while ("<<e<<") {\n";
}
picode->invalidate();
break;
case REPEAT_TYPE:
ostr << "\n"<<indentStr(indLevel)<<"do {\n";
picode = &latch->back();
picode->invalidate();
break;
case ENDLESS_TYPE:
ostr << "\n"<<indentStr(indLevel)<<"for (;;) {\n";
}
cCode.appendCode(ostr.str());
stats.numHLIcode += 1;
indLevel++;
} }
/* Write the code for this basic block */ /* Write the code for this basic block */
@ -211,18 +241,16 @@ void BB::writeCode (int indLevel, Function * pProc , int *numLoc,int _latchNode,
} }
/* Check for end of path */ /* Check for end of path */
_nodeType = nodeType; if (isEndOfPath(_latchNode))
if (_nodeType == RETURN_NODE || _nodeType == TERMINATE_NODE ||
_nodeType == NOWHERE_NODE || (dfsLastNum == _latchNode))
return; return;
/* Check type of loop/node and process code */ /* Check type of loop/node and process code */
if (_loopType) /* there is a loop */ if ( loopType) /* there is a loop */
{ {
assert(latch); assert(latch);
if (this != latch) /* loop is over several bbs */ if (this != latch) /* loop is over several bbs */
{ {
if (_loopType == WHILE_TYPE) if (loopType == WHILE_TYPE)
{ {
succ = edges[THEN].BBptr; succ = edges[THEN].BBptr;
if (succ->dfsLastNum == loopFollow) if (succ->dfsLastNum == loopFollow)
@ -238,7 +266,7 @@ void BB::writeCode (int indLevel, Function * pProc , int *numLoc,int _latchNode,
/* Loop epilogue: generate the loop trailer */ /* Loop epilogue: generate the loop trailer */
indLevel--; indLevel--;
if (_loopType == WHILE_TYPE) if (loopType == WHILE_TYPE)
{ {
std::ostringstream ostr; std::ostringstream ostr;
/* Check if there is need to repeat other statements involved /* Check if there is need to repeat other statements involved
@ -250,9 +278,9 @@ void BB::writeCode (int indLevel, Function * pProc , int *numLoc,int _latchNode,
ostr <<indentStr(indLevel)<< "} /* end of while */\n"; ostr <<indentStr(indLevel)<< "} /* end of while */\n";
cCode.appendCode(ostr.str()); cCode.appendCode(ostr.str());
} }
else if (_loopType == ENDLESS_TYPE) else if (loopType == ENDLESS_TYPE)
cCode.appendCode( "%s} /* end of loop */\n",indentStr(indLevel)); cCode.appendCode( "%s} /* end of loop */\n",indentStr(indLevel));
else if (_loopType == REPEAT_TYPE) else if (loopType == REPEAT_TYPE)
{ {
if (picode->hl()->opcode != HLI_JCOND) if (picode->hl()->opcode != HLI_JCOND)
reportError (REPEAT_FAIL); reportError (REPEAT_FAIL);
@ -275,7 +303,7 @@ void BB::writeCode (int indLevel, Function * pProc , int *numLoc,int _latchNode,
else /* no loop, process nodeType of the graph */ else /* no loop, process nodeType of the graph */
{ {
if (_nodeType == TWO_BRANCH) /* if-then[-else] */ if (nodeType == TWO_BRANCH) /* if-then[-else] */
{ {
stats.numHLIcode++; stats.numHLIcode++;
indLevel++; indLevel++;
@ -344,8 +372,11 @@ void BB::writeCode (int indLevel, Function * pProc , int *numLoc,int _latchNode,
else /* fall, call, 1w */ else /* fall, call, 1w */
{ {
succ = edges[0].BBptr; /* fall-through edge */ succ = edges[0].BBptr; /* fall-through edge */
assert(succ->size()>0);
if (succ->traversed != DFS_ALPHA) if (succ->traversed != DFS_ALPHA)
{
succ->writeCode (indLevel, pProc,numLoc, _latchNode,_ifFollow); succ->writeCode (indLevel, pProc,numLoc, _latchNode,_ifFollow);
}
} }
} }
} }
@ -361,7 +392,7 @@ void BB::writeBB(std::ostream &ostr,int lev, Function * pProc, int *numLoc)
/* Generate code for each hlicode that is not a HLI_JCOND */ /* Generate code for each hlicode that is not a HLI_JCOND */
for(ICODE &pHli : *this) for(ICODE &pHli : instructions)
{ {
if ((pHli.type == HIGH_LEVEL) && ( pHli.valid() )) //TODO: use filtering range here. if ((pHli.type == HIGH_LEVEL) && ( pHli.valid() )) //TODO: use filtering range here.
{ {
@ -379,33 +410,34 @@ void BB::writeBB(std::ostream &ostr,int lev, Function * pProc, int *numLoc)
iICODE BB::begin() iICODE BB::begin()
{ {
return range_start; return instructions.begin();//range_start;
} }
iICODE BB::end() const iICODE BB::end() const
{ {
return range_end; return instructions.end();//range_end
} }
ICODE &BB::back() ICODE &BB::back()
{ {
return *rbegin(); return instructions.back();//*rbegin();
} }
size_t BB::size() size_t BB::size()
{ {
return distance(range_start,range_end);
return distance(instructions.begin(),instructions.end());
} }
ICODE &BB::front() ICODE &BB::front()
{ {
return *begin(); return instructions.front();//*begin();
} }
riICODE BB::rbegin() riICODE BB::rbegin()
{ {
return riICODE(end()); return riICODE( instructions.end() );
} }
riICODE BB::rend() riICODE BB::rend()
{ {
return riICODE(begin()); return riICODE( instructions.begin() );
} }

View File

@ -823,7 +823,7 @@ void COND_EXPR::changeBoolOp (condOp newOp)
/* Inserts the expression exp into the tree at the location specified by the /* Inserts the expression exp into the tree at the location specified by the
* register regi */ * register regi */
bool COND_EXPR::insertSubTreeReg (COND_EXPR *&tree, COND_EXPR *_expr, eReg regi,LOCAL_ID *locsym) bool COND_EXPR::insertSubTreeReg (COND_EXPR *&tree, COND_EXPR *_expr, eReg regi,const LOCAL_ID *locsym)
{ {
if (tree == NULL) if (tree == NULL)
@ -836,7 +836,7 @@ bool COND_EXPR::insertSubTreeReg (COND_EXPR *&tree, COND_EXPR *_expr, eReg regi,
} }
return false; return false;
} }
COND_EXPR *COND_EXPR::insertSubTreeReg (COND_EXPR *_expr, eReg regi,LOCAL_ID *locsym) COND_EXPR *COND_EXPR::insertSubTreeReg (COND_EXPR *_expr, eReg regi,const LOCAL_ID *locsym)
{ {
eReg treeReg; eReg treeReg;

View File

@ -2,14 +2,16 @@
* Description : Performs control flow analysis on the CFG * Description : Performs control flow analysis on the CFG
* (C) Cristina Cifuentes * (C) Cristina Cifuentes
********************************************************************/ ********************************************************************/
#include <boost/range/algorithm.hpp>
#include <algorithm> #include <algorithm>
#include <list> #include <list>
#include <cassert> #include <cassert>
#include "dcc.h"
#include <stdio.h> #include <stdio.h>
#include <string.h> #include <string.h>
#include <malloc.h> #include <malloc.h>
#include "dcc.h"
//typedef struct list { //typedef struct list {
// int nodeIdx; // int nodeIdx;
// struct list *next; // struct list *next;
@ -577,6 +579,7 @@ bool Function::Case_X_or_Y(BB* pbb, BB* thenBB, BB* elseBB)
hl1.expr(COND_EXPR::boolOp (hl1.expr(), hl2.expr(), DBL_OR)); hl1.expr(COND_EXPR::boolOp (hl1.expr(), hl2.expr(), DBL_OR));
/* Replace in-edge to obb from t to pbb */ /* Replace in-edge to obb from t to pbb */
auto iter=find(obb->inEdges.begin(),obb->inEdges.end(),thenBB); auto iter=find(obb->inEdges.begin(),obb->inEdges.end(),thenBB);
if(iter!=obb->inEdges.end()) if(iter!=obb->inEdges.end())
*iter = pbb; *iter = pbb;

View File

@ -9,6 +9,7 @@
#include <boost/range.hpp> #include <boost/range.hpp>
#include <boost/range/adaptors.hpp> #include <boost/range/adaptors.hpp>
#include <boost/range/algorithm.hpp> #include <boost/range/algorithm.hpp>
#include <boost/assign.hpp>
#include <string.h> #include <string.h>
#include <iostream> #include <iostream>
#include <iomanip> #include <iomanip>
@ -24,6 +25,13 @@ struct ExpStack
COND_EXPR * pop(); COND_EXPR * pop();
int numElem(); int numElem();
boolT empty(); boolT empty();
void processExpPush(int &numHlIcodes, iICODE picode)
{
push(picode->hl()->expr());
picode->invalidate();
numHlIcodes--;
}
}; };
/*************************************************************************** /***************************************************************************
* Expression stack functions * Expression stack functions
@ -266,6 +274,8 @@ void Function::genLiveKtes ()
* Propagates register usage information to the procedure call. */ * Propagates register usage information to the procedure call. */
void Function::liveRegAnalysis (std::bitset<32> &in_liveOut) void Function::liveRegAnalysis (std::bitset<32> &in_liveOut)
{ {
using namespace boost::adaptors;
using namespace boost::assign;
BB * pbb=0; /* pointer to current basic block */ BB * pbb=0; /* pointer to current basic block */
Function * pcallee; /* invoked subroutine */ Function * pcallee; /* invoked subroutine */
//ICODE *ticode /* icode that invokes a subroutine */ //ICODE *ticode /* icode that invokes a subroutine */
@ -282,14 +292,10 @@ void Function::liveRegAnalysis (std::bitset<32> &in_liveOut)
{ {
/* Process nodes in reverse postorder order */ /* Process nodes in reverse postorder order */
change = false; change = false;
//for (i = numBBs; i > 0; i--) auto valid_reversed_bbs = (m_dfsLast | reversed | filtered(BB::ValidFunctor()) );
//boost::RandomAccessContainerConcept; for( BB * _pbb : valid_reversed_bbs)
for(auto iBB=m_dfsLast.rbegin(); iBB!=m_dfsLast.rend(); ++iBB)
{ {
pbb = *iBB;//m_dfsLast[i-1]; pbb = _pbb;//*iBB;//m_dfsLast[i-1];
if (pbb->flg & INVALID_BB) /* Do not process invalid BBs */
continue;
/* Get current liveIn() and liveOut() sets */ /* Get current liveIn() and liveOut() sets */
prevLiveIn = pbb->liveIn; prevLiveIn = pbb->liveIn;
@ -307,7 +313,6 @@ void Function::liveRegAnalysis (std::bitset<32> &in_liveOut)
auto picode = pbb->rbegin(); /* icode of function return */ auto picode = pbb->rbegin(); /* icode of function return */
if (picode->hl()->opcode == HLI_RET) if (picode->hl()->opcode == HLI_RET)
{ {
//pbb->back().loc_ip
picode->hl()->expr(COND_EXPR::idID (&retVal, &localId, (++pbb->rbegin()).base())); picode->hl()->expr(COND_EXPR::idID (&retVal, &localId, (++pbb->rbegin()).base()));
picode->du.use = in_liveOut; picode->du.use = in_liveOut;
} }
@ -393,6 +398,7 @@ void Function::liveRegAnalysis (std::bitset<32> &in_liveOut)
void BB::genDU1() void BB::genDU1()
{ {
using namespace boost::adaptors;
eReg regi; /* Register that was defined */ eReg regi; /* Register that was defined */
int k, defRegIdx, useIdx; int k, defRegIdx, useIdx;
iICODE picode, ticode,lastInst; iICODE picode, ticode,lastInst;
@ -404,10 +410,13 @@ void BB::genDU1()
*/ */
assert(0!=Parent); assert(0!=Parent);
lastInst = this->end(); lastInst = this->end();
for (picode = this->begin(); picode != lastInst; picode++) ICODE::TypeFilter<HIGH_LEVEL> zq;
auto all_high_levels = instructions | filtered(zq);
printf("\n");
for (auto picode=all_high_levels.begin(); picode!=all_high_levels.end(); ++picode)
{ {
if (picode->type != HIGH_LEVEL) // if (picode->type != HIGH_LEVEL)
continue; // continue;
regi = rUNDEF; regi = rUNDEF;
defRegIdx = 0; defRegIdx = 0;
// foreach defined register // foreach defined register
@ -428,10 +437,10 @@ void BB::genDU1()
continue; continue;
if ((regi == rSI) && (flg & SI_REGVAR)) if ((regi == rSI) && (flg & SI_REGVAR))
continue; continue;
if (distance(picode,lastInst)>1) /* several instructions */ if (distance(picode,all_high_levels.end())>1) /* several instructions */
{ {
useIdx = 0; useIdx = 0;
for (auto ricode = ++iICODE(picode); ricode != lastInst; ricode++) for (auto ricode = ++iICODE(picode.base()); ricode != lastInst; ricode++)
{ {
ticode=ricode; ticode=ricode;
if (ricode->type != HIGH_LEVEL) // Only check uses of HIGH_LEVEL icodes if (ricode->type != HIGH_LEVEL) // Only check uses of HIGH_LEVEL icodes
@ -503,9 +512,9 @@ void BB::genDU1()
/* Backpatch any uses of this instruction, within /* Backpatch any uses of this instruction, within
* the same BB, if the instruction was invalidated */ * the same BB, if the instruction was invalidated */
for (auto back_patch_at = riICODE(picode); back_patch_at != rend(); back_patch_at++) for (auto back_patch_at = riICODE(picode.base()); back_patch_at != rend(); back_patch_at++)
{ {
back_patch_at->du1.remove(0,picode); back_patch_at->du1.remove(0,picode.base());
} }
} }
else /* liveOut */ else /* liveOut */
@ -536,18 +545,15 @@ void Function::genDU1 ()
/* Substitutes the rhs (or lhs if rhs not possible) of ticode for the rhs /* Substitutes the rhs (or lhs if rhs not possible) of ticode for the rhs
* of picode. */ * of picode. */
static void forwardSubs (COND_EXPR *lhs, COND_EXPR *rhs, iICODE picode, void LOCAL_ID::forwardSubs (COND_EXPR *lhs, COND_EXPR *rhs, iICODE picode, iICODE ticode, int &numHlIcodes) const
iICODE ticode, LOCAL_ID *locsym, int &numHlIcodes)
{ {
boolT res; bool res;
if (rhs == NULL) /* In case expression popped is NULL */ if (rhs == NULL) /* In case expression popped is NULL */
return; return;
/* Insert on rhs of ticode, if possible */ /* Insert on rhs of ticode, if possible */
res = COND_EXPR::insertSubTreeReg (ticode->hl()->asgn.rhs,rhs, res = COND_EXPR::insertSubTreeReg (ticode->hl()->asgn.rhs,rhs, id_arr[lhs->expr.ident.idNode.regiIdx].id.regi, this);
locsym->id_arr[lhs->expr.ident.idNode.regiIdx].id.regi,
locsym);
if (res) if (res)
{ {
picode->invalidate(); picode->invalidate();
@ -556,9 +562,7 @@ static void forwardSubs (COND_EXPR *lhs, COND_EXPR *rhs, iICODE picode,
else else
{ {
/* Try to insert it on lhs of ticode*/ /* Try to insert it on lhs of ticode*/
res = COND_EXPR::insertSubTreeReg (ticode->hl()->asgn.lhs,rhs, res = COND_EXPR::insertSubTreeReg (ticode->hl()->asgn.lhs,rhs, id_arr[lhs->expr.ident.idNode.regiIdx].id.regi, this);
locsym->id_arr[lhs->expr.ident.idNode.regiIdx].id.regi,
locsym);
if (res) if (res)
{ {
picode->invalidate(); picode->invalidate();
@ -599,7 +603,7 @@ static void forwardSubsLong (int longIdx, COND_EXPR *_exp, iICODE picode, iICODE
/* Returns whether the elements of the expression rhs are all x-clear from /* Returns whether the elements of the expression rhs are all x-clear from
* instruction f up to instruction t. */ * instruction f up to instruction t. */
bool COND_EXPR::xClear (iICODE f, iICODE t, iICODE lastBBinst, Function * pproc) bool COND_EXPR::xClear (iICODE f, iICODE t, iICODE lastBBinst, const LOCAL_ID & locId)
{ {
iICODE i; iICODE i;
boolT res; boolT res;
@ -610,7 +614,7 @@ bool COND_EXPR::xClear (iICODE f, iICODE t, iICODE lastBBinst, Function * pproc)
case IDENTIFIER: case IDENTIFIER:
if (expr.ident.idType == REGISTER) if (expr.ident.idType == REGISTER)
{ {
regi= pproc->localId.id_arr[expr.ident.idNode.regiIdx].id.regi; regi= locId.id_arr[expr.ident.idNode.regiIdx].id.regi;
for (i = ++iICODE(f); (i != lastBBinst) && (i!=t); i++) for (i = ++iICODE(f); (i != lastBBinst) && (i!=t); i++)
if ((i->type == HIGH_LEVEL) && ( i->valid() )) if ((i->type == HIGH_LEVEL) && ( i->valid() ))
{ {
@ -631,38 +635,38 @@ bool COND_EXPR::xClear (iICODE f, iICODE t, iICODE lastBBinst, Function * pproc)
case BOOLEAN_OP: case BOOLEAN_OP:
if(0==rhs()) if(0==rhs())
return false; return false;
res = rhs()->xClear ( f, t, lastBBinst, pproc); res = rhs()->xClear ( f, t, lastBBinst, locId);
if (res == false) if (res == false)
return false; return false;
if(0==lhs()) if(0==lhs())
return false; return false;
return lhs()->xClear ( f, t, lastBBinst, pproc); return lhs()->xClear ( f, t, lastBBinst, locId);
case NEGATION: case NEGATION:
case ADDRESSOF: case ADDRESSOF:
case DEREFERENCE: case DEREFERENCE:
if(0==expr.unaryExp) if(0==expr.unaryExp)
return false; return false;
return expr.unaryExp->xClear ( f, t, lastBBinst, pproc); return expr.unaryExp->xClear ( f, t, lastBBinst, locId);
} /* eos */ } /* eos */
return false; return false;
} }
bool UnaryOperator::xClear(iICODE f, iICODE t, iICODE lastBBinst, Function *pproc) bool UnaryOperator::xClear(iICODE f, iICODE t, iICODE lastBBinst, const LOCAL_ID &locs)
{ {
if(0==unaryExp) if(0==unaryExp)
return false; return false;
return unaryExp->xClear ( f, t, lastBBinst, pproc); return unaryExp->xClear ( f, t, lastBBinst, locs);
} }
bool BinaryOperator::xClear(iICODE f, iICODE t, iICODE lastBBinst, Function *pproc) bool BinaryOperator::xClear(iICODE f, iICODE t, iICODE lastBBinst, const LOCAL_ID &locs)
{ {
if(0==m_rhs) if(0==m_rhs)
return false; return false;
if ( ! m_rhs->xClear (f, t, lastBBinst, pproc) ) if ( ! m_rhs->xClear (f, t, lastBBinst, locs) )
return false; return false;
if(0==m_lhs) if(0==m_lhs)
return false; return false;
return m_lhs->xClear (f, t, lastBBinst, pproc); return m_lhs->xClear (f, t, lastBBinst, locs);
} }
/* Checks the type of the formal argument as against to the actual argument, /* Checks the type of the formal argument as against to the actual argument,
* whenever possible, and then places the actual argument on the procedure's * whenever possible, and then places the actual argument on the procedure's
@ -712,37 +716,39 @@ static int processCArg (Function * pp, Function * pProc, ICODE * picode, int num
/** Eliminates extraneous intermediate icode instructions when finding /** Eliminates extraneous intermediate icode instructions when finding
* expressions. Generates new hlIcodes in the form of expression trees. * expressions. Generates new hlIcodes in the form of expression trees.
* For HLI_CALL hlIcodes, places the arguments in the argument list. */ * For HLI_CALL hlIcodes, places the arguments in the argument list. */
void Function::processTargetIcode(iICODE picode, int &numHlIcodes, iICODE ticode,bool isLong) void LOCAL_ID::processTargetIcode(iICODE picode, int &numHlIcodes, iICODE ticode,bool isLong) const
{ {
boolT res; boolT res;
switch (ticode->hl()->opcode) { HLTYPE &p_hl(*picode->hl());
HLTYPE &t_hl(*ticode->hl());
switch (t_hl.opcode)
{
case HLI_ASSIGN: case HLI_ASSIGN:
if(isLong) if(isLong)
{ {
forwardSubsLong (picode->hl()->asgn.lhs->expr.ident.idNode.longIdx, forwardSubsLong (p_hl.asgn.lhs->expr.ident.idNode.longIdx,
picode->hl()->asgn.rhs, picode,ticode, p_hl.asgn.rhs, picode,ticode,
&numHlIcodes); &numHlIcodes);
} }
else else
forwardSubs (picode->hl()->asgn.lhs, picode->hl()->asgn.rhs, this->forwardSubs (p_hl.asgn.lhs, p_hl.asgn.rhs, picode, ticode, numHlIcodes);
picode, ticode, &localId, numHlIcodes);
break; break;
case HLI_JCOND: case HLI_PUSH: case HLI_RET: case HLI_JCOND: case HLI_PUSH: case HLI_RET:
if(isLong) if(isLong)
{ {
res = COND_EXPR::insertSubTreeLongReg ( res = COND_EXPR::insertSubTreeLongReg (
picode->hl()->asgn.rhs, p_hl.asgn.rhs,
&ticode->hl()->exp.v, &t_hl.exp.v,
picode->hl()->asgn.lhs->expr.ident.idNode.longIdx); p_hl.asgn.lhs->expr.ident.idNode.longIdx);
} }
else else
{ {
res = COND_EXPR::insertSubTreeReg ( res = COND_EXPR::insertSubTreeReg (
ticode->hl()->exp.v, t_hl.exp.v,
picode->hl()->asgn.rhs, p_hl.asgn.rhs,
localId.id_arr[picode->hl()->asgn.lhs->expr.ident.idNode.regiIdx].id.regi, id_arr[p_hl.asgn.lhs->expr.ident.idNode.regiIdx].id.regi,
&localId); this);
} }
if (res) if (res)
{ {
@ -821,274 +827,282 @@ void Function::processHliCall(COND_EXPR *_exp, iICODE picode)
} }
} }
void Function::findExps()
int BB::findBBExps(LOCAL_ID &locals,Function *fnc)
{ {
int i, numHlIcodes; bool res;
iICODE
picode, // Current icode */ ID *_retVal; // function return value
ticode; // Target icode */
BB * pbb; // Current and next basic block */
boolT res;
COND_EXPR *_exp, // expression pointer - for HLI_POP and HLI_CALL */ COND_EXPR *_exp, // expression pointer - for HLI_POP and HLI_CALL */
*lhs; // exp ptr for return value of a HLI_CALL */ *lhs; // exp ptr for return value of a HLI_CALL */
//STKFRAME * args; // pointer to arguments - for HLI_CALL */ iICODE ticode; // Target icode */
uint8_t regi; // register(s) to be forward substituted */ HLTYPE *ti_hl=0;
ID *_retVal; // function return value uint8_t regi;
numHlIcodes = 0;
/* Initialize expression stack */ // register(s) to be forward substituted */
g_exp_stk.init(); for (iICODE picode = begin(); picode != end(); picode++)
_exp = 0;
/* Traverse tree in dfsLast order */
for (i = 0; i < numBBs; i++)
{ {
/* Process one BB */ if ((picode->type != HIGH_LEVEL) || ( ! picode->valid() ))
pbb = m_dfsLast[i];
if (pbb->flg & INVALID_BB)
continue; continue;
numHlIcodes = 0; HLTYPE &_icHl(*picode->hl());
for (picode = pbb->begin(); picode != pbb->end(); picode++) numHlIcodes++;
if (picode->du1.numRegsDef == 1) /* uint8_t/uint16_t regs */
{ {
if ((picode->type != HIGH_LEVEL) || ( ! picode->valid() )) /* Check for only one use of this register. If this is
continue; * the last definition of the register in this BB, check
numHlIcodes++; * that it is not liveOut from this basic block */
if (picode->du1.numRegsDef == 1) /* uint8_t/uint16_t regs */ if (picode->du1.numUses(0)==1)
{ {
/* Check for only one use of this register. If this is /* Check that this register is not liveOut, if it
* the last definition of the register in this BB, check * is the last definition of the register */
* that it is not liveOut from this basic block */ regi = picode->du1.regi[0];
if (picode->du1.numUses(0)==1)
/* Check if we can forward substitute this register */
switch (_icHl.opcode)
{ {
/* Check that this register is not liveOut, if it case HLI_ASSIGN:
* is the last definition of the register */ /* Replace rhs of current icode into target
regi = picode->du1.regi[0];
/* Check if we can forward substitute this register */
switch (picode->hl()->opcode)
{
case HLI_ASSIGN:
/* Replace rhs of current icode into target
* icode expression */ * icode expression */
ticode = picode->du1.idx[0].uses.front();
if ((picode->du.lastDefRegi & duReg[regi]).any() &&
((ticode->hl()->opcode != HLI_CALL) &&
(ticode->hl()->opcode != HLI_RET)))
continue;
if (_icHl.asgn.rhs->xClear (picode,
picode->du1.idx[0].uses[0],
end(), locals))
{
locals.processTargetIcode(picode, numHlIcodes, ticode,false);
}
break;
case HLI_POP:
ticode = picode->du1.idx[0].uses.front();
ti_hl = ticode->hl();
if ((picode->du.lastDefRegi & duReg[regi]).any() &&
((ti_hl->opcode != HLI_CALL) &&
(ti_hl->opcode != HLI_RET)))
continue;
_exp = g_exp_stk.pop(); /* pop last exp pushed */
switch (ticode->hl()->opcode) {
case HLI_ASSIGN:
locals.forwardSubs(_icHl.expr(), _exp, picode, ticode, numHlIcodes);
break;
case HLI_JCOND: case HLI_PUSH: case HLI_RET:
res = COND_EXPR::insertSubTreeReg (ti_hl->exp.v,
_exp,
locals.id_arr[_icHl.expr()->expr.ident.idNode.regiIdx].id.regi,
&locals);
if (res)
{
picode->invalidate();
numHlIcodes--;
}
break;
/****case HLI_CALL: /* register arguments
newRegArg (pProc, picode, ticode);
picode->invalidate();
numHlIcodes--;
break; */
} /* eos */
break;
case HLI_CALL:
ticode = picode->du1.idx[0].uses.front();
ti_hl = ticode->hl();
_retVal = &_icHl.call.proc->retVal;
switch (ti_hl->opcode)
{
case HLI_ASSIGN:
assert(ti_hl->asgn.rhs);
_exp = _icHl.call.toId();
res = COND_EXPR::insertSubTreeReg (ti_hl->asgn.rhs,_exp, _retVal->id.regi, &locals);
if (! res)
COND_EXPR::insertSubTreeReg (ti_hl->asgn.lhs, _exp,_retVal->id.regi, &locals);
//TODO: HERE missing: 2 regs
picode->invalidate();
numHlIcodes--;
break;
case HLI_PUSH: case HLI_RET:
ti_hl->expr( _icHl.call.toId() );
picode->invalidate();
numHlIcodes--;
break;
case HLI_JCOND:
_exp = _icHl.call.toId();
res = COND_EXPR::insertSubTreeReg (ti_hl->exp.v, _exp, _retVal->id.regi, &locals);
if (res) /* was substituted */
{
picode->invalidate();
numHlIcodes--;
}
else /* cannot substitute function */
{
//picode->loc_ip
lhs = COND_EXPR::idID(_retVal,&locals,picode);
picode->setAsgn(lhs, _exp);
}
break;
} /* eos */
break;
} /* eos */
}
}
else if (picode->du1.numRegsDef == 2) /* long regs */
{
/* Check for only one use of these registers */
if ((picode->du1.numUses(0) == 1) and (picode->du1.numUses(1) == 1))
{
regi = picode->du1.regi[0]; //TODO: verify that regi actually should be assigned this
switch (_icHl.opcode)
{
case HLI_ASSIGN:
/* Replace rhs of current icode into target
* icode expression */
if (picode->du1.idx[0].uses[0] == picode->du1.idx[1].uses[0])
{
ticode = picode->du1.idx[0].uses.front();
if ((picode->du.lastDefRegi & duReg[regi]).any() &&
((ticode->hl()->opcode != HLI_CALL) &&
(ticode->hl()->opcode != HLI_RET)))
continue;
locals.processTargetIcode(picode, numHlIcodes, ticode,true);
}
break;
case HLI_POP:
if (picode->du1.idx[0].uses[0] == picode->du1.idx[1].uses[0])
{
ticode = picode->du1.idx[0].uses.front(); ticode = picode->du1.idx[0].uses.front();
if ((picode->du.lastDefRegi & duReg[regi]).any() && if ((picode->du.lastDefRegi & duReg[regi]).any() &&
((ticode->hl()->opcode != HLI_CALL) && ((ticode->hl()->opcode != HLI_CALL) &&
(ticode->hl()->opcode != HLI_RET))) (ticode->hl()->opcode != HLI_RET)))
continue; continue;
if (picode->hl()->asgn.rhs->xClear (picode, _exp = g_exp_stk.pop(); /* pop last exp pushed */
picode->du1.idx[0].uses[0], pbb->end(), this))
{
processTargetIcode(picode, numHlIcodes, ticode,false);
}
break;
case HLI_POP:
ticode = picode->du1.idx[0].uses.front();
if ((picode->du.lastDefRegi & duReg[regi]).any() &&
((ticode->hl()->opcode != HLI_CALL) &&
(ticode->hl()->opcode != HLI_RET)))
continue;
_exp = g_exp_stk.pop(); /* pop last exp pushed */
switch (ticode->hl()->opcode) { switch (ticode->hl()->opcode) {
case HLI_ASSIGN: case HLI_ASSIGN:
forwardSubs (picode->hl()->expr(), _exp, forwardSubsLong (_icHl.expr()->expr.ident.idNode.longIdx,
picode, ticode, &localId, _exp, picode, ticode, &numHlIcodes);
numHlIcodes);
break; break;
case HLI_JCOND: case HLI_PUSH:
case HLI_JCOND: case HLI_PUSH: case HLI_RET: res = COND_EXPR::insertSubTreeLongReg (_exp,
res = COND_EXPR::insertSubTreeReg (ticode->hl()->exp.v, &ticode->hl()->exp.v,
_exp, _icHl.asgn.lhs->expr.ident.idNode.longIdx);
localId.id_arr[picode->hl()->expr()->expr.ident.idNode.regiIdx].id.regi,
&localId);
if (res) if (res)
{ {
picode->invalidate(); picode->invalidate();
numHlIcodes--; numHlIcodes--;
} }
break; break;
case HLI_CALL: /*** missing ***/
/****case HLI_CALL: /* register arguments
newRegArg (pProc, picode, ticode);
picode->invalidate();
numHlIcodes--;
break; */
} /* eos */
break;
case HLI_CALL:
ticode = picode->du1.idx[0].uses.front();
HLTYPE *ti_hl(ticode->hl());
_retVal = &picode->hl()->call.proc->retVal;
switch (ti_hl->opcode) {
case HLI_ASSIGN:
assert(ti_hl->asgn.rhs);
_exp = COND_EXPR::idFunc ( picode->hl()->call.proc, picode->hl()->call.args);
res = COND_EXPR::insertSubTreeReg (ti_hl->asgn.rhs,_exp, _retVal->id.regi, &localId);
if (! res)
COND_EXPR::insertSubTreeReg (ti_hl->asgn.lhs, _exp,_retVal->id.regi, &localId);
//TODO: HERE missing: 2 regs
picode->invalidate();
numHlIcodes--;
break;
case HLI_PUSH: case HLI_RET:
ti_hl->expr( COND_EXPR::idFunc ( picode->hl()->call.proc, picode->hl()->call.args) );
picode->invalidate();
numHlIcodes--;
break;
case HLI_JCOND:
_exp = COND_EXPR::idFunc ( picode->hl()->call.proc, picode->hl()->call.args);
res = COND_EXPR::insertSubTreeReg (ti_hl->exp.v, _exp, _retVal->id.regi, &localId);
if (res) /* was substituted */
{
picode->invalidate();
numHlIcodes--;
}
else /* cannot substitute function */
{
//picode->loc_ip
lhs = COND_EXPR::idID(_retVal,&localId,picode);
picode->setAsgn(lhs, _exp);
}
break; break;
} /* eos */ } /* eos */
break; }
} /* eos */ break;
}
}
else if (picode->du1.numRegsDef == 2) /* long regs */ case HLI_CALL: /* check for function return */
{ ticode = picode->du1.idx[0].uses.front();
/* Check for only one use of these registers */ switch (ticode->hl()->opcode)
if ((picode->du1.numUses(0) == 1) and (picode->du1.numUses(1) == 1)) {
{ case HLI_ASSIGN:
regi = picode->du1.regi[0]; //TODO: verify that regi actually should be assigned this _exp = _icHl.call.toId();
ticode->hl()->asgn.lhs =
COND_EXPR::idLong(&locals, DST, ticode,HIGH_FIRST, picode, eDEF, ++iICODE(ticode));
ticode->hl()->asgn.rhs = _exp;
picode->invalidate();
numHlIcodes--;
break;
switch (picode->hl()->opcode) { case HLI_PUSH: case HLI_RET:
case HLI_ASSIGN: ticode->hl()->expr( _icHl.call.toId() );
/* Replace rhs of current icode into target picode->invalidate();
* icode expression */ numHlIcodes--;
if (picode->du1.idx[0].uses[0] == picode->du1.idx[1].uses[0]) break;
{
ticode = picode->du1.idx[0].uses.front();
if ((picode->du.lastDefRegi & duReg[regi]).any() &&
((ticode->hl()->opcode != HLI_CALL) &&
(ticode->hl()->opcode != HLI_RET)))
continue;
processTargetIcode(picode, numHlIcodes, ticode,true);
}
break;
case HLI_POP: case HLI_JCOND:
if (picode->du1.idx[0].uses[0] == picode->du1.idx[1].uses[0]) _exp = _icHl.call.toId();
{ _retVal = &picode->hl()->call.proc->retVal;
ticode = picode->du1.idx[0].uses.front(); res = COND_EXPR::insertSubTreeLongReg (_exp,
if ((picode->du.lastDefRegi & duReg[regi]).any() && &ticode->hl()->exp.v,
((ticode->hl()->opcode != HLI_CALL) && locals.newLongReg ( _retVal->type, _retVal->id.longId.h,
(ticode->hl()->opcode != HLI_RET))) _retVal->id.longId.l, picode));
continue; if (res) /* was substituted */
{
_exp = g_exp_stk.pop(); /* pop last exp pushed */
switch (ticode->hl()->opcode) {
case HLI_ASSIGN:
forwardSubsLong (picode->hl()->expr()->expr.ident.idNode.longIdx,
_exp, picode, ticode, &numHlIcodes);
break;
case HLI_JCOND: case HLI_PUSH:
res = COND_EXPR::insertSubTreeLongReg (_exp,
&ticode->hl()->exp.v,
picode->hl()->asgn.lhs->expr.ident.idNode.longIdx);
if (res)
{
picode->invalidate();
numHlIcodes--;
}
break;
case HLI_CALL: /*** missing ***/
break;
} /* eos */
}
break;
case HLI_CALL: /* check for function return */
ticode = picode->du1.idx[0].uses.front();
switch (ticode->hl()->opcode)
{
case HLI_ASSIGN:
_exp = COND_EXPR::idFunc ( picode->hl()->call.proc, picode->hl()->call.args);
ticode->hl()->asgn.lhs =
COND_EXPR::idLong(&localId, DST, ticode,HIGH_FIRST, picode, eDEF, ++iICODE(ticode));
ticode->hl()->asgn.rhs = _exp;
picode->invalidate(); picode->invalidate();
numHlIcodes--; numHlIcodes--;
break; }
else /* cannot substitute function */
case HLI_PUSH: case HLI_RET: {
ticode->hl()->expr( COND_EXPR::idFunc ( picode->hl()->call.proc, picode->hl()->call.args) ); lhs = locals.createId(_retVal,picode);
picode->invalidate(); picode->setAsgn(lhs, _exp);
numHlIcodes--; }
break; break;
} /* eos */
case HLI_JCOND: } /* eos */
_exp = COND_EXPR::idFunc ( picode->hl()->call.proc, picode->hl()->call.args);
_retVal = &picode->hl()->call.proc->retVal;
res = COND_EXPR::insertSubTreeLongReg (_exp,
&ticode->hl()->exp.v,
localId.newLongReg ( _retVal->type, _retVal->id.longId.h,
_retVal->id.longId.l, picode));
if (res) /* was substituted */
{
picode->invalidate();
numHlIcodes--;
}
else /* cannot substitute function */
{
lhs = COND_EXPR::idID(_retVal,&localId,picode/*picode->loc_ip*/);
picode->setAsgn(lhs, _exp);
}
break;
} /* eos */
} /* eos */
}
} }
}
/* HLI_PUSH doesn't define any registers, only uses registers.
* Push the associated expression to the register on the local
* expression stack */
else if (_icHl.opcode == HLI_PUSH)
{
g_exp_stk.processExpPush(numHlIcodes, picode);
}
else if(picode->du1.numRegsDef!=0)
printf("Num def %d\n",picode->du1.numRegsDef);
/* HLI_PUSH doesn't define any registers, only uses registers. /* For HLI_CALL instructions that use arguments from the stack,
* Push the associated expression to the register on the local * pop them from the expression stack and place them on the
* expression stack */ * procedure's argument list */
else if (picode->hl()->opcode == HLI_PUSH) if(_icHl.opcode == HLI_CALL)
{
if ( not _icHl.call.proc->hasRegArgs())
{ {
g_exp_stk.push(picode->hl()->expr()); fnc->processHliCall(_exp, picode);
picode->invalidate();
numHlIcodes--;
}
/* For HLI_CALL instructions that use arguments from the stack,
* pop them from the expression stack and place them on the
* procedure's argument list */
if ((picode->hl()->opcode == HLI_CALL) && ! (picode->hl()->call.proc->flg & REG_ARGS))
{
processHliCall(_exp, picode);
} }
/* If we could not substitute the result of a function, /* If we could not substitute the result of a function,
* assign it to the corresponding registers */ * assign it to the corresponding registers */
if ((picode->hl()->opcode == HLI_CALL) && if ( not _icHl.call.proc->isLibrary() and (not picode->du1.used(0)) and (picode->du1.numRegsDef > 0))
((picode->hl()->call.proc->flg & PROC_ISLIB) !=
PROC_ISLIB) && (not picode->du1.used(0)) &&
(picode->du1.numRegsDef > 0))
{ {
_exp = COND_EXPR::idFunc (picode->hl()->call.proc, picode->hl()->call.args); _exp = COND_EXPR::idFunc (_icHl.call.proc, _icHl.call.args);
lhs = COND_EXPR::idID (&picode->hl()->call.proc->retVal, &localId, picode); lhs = COND_EXPR::idID (&_icHl.call.proc->retVal, &locals, picode);
picode->setAsgn(lhs, _exp); picode->setAsgn(lhs, _exp);
} }
} }
}
/* Store number of high-level icodes in current basic block */
}
void Function::findExps()
{
//int i, numHlIcodes;
//STKFRAME * args; // pointer to arguments - for HLI_CALL */
/* Initialize expression stack */
g_exp_stk.init();
/* Traverse tree in dfsLast order */
// for (i = 0; i < numBBs; i++)
for(BB *pbb : m_dfsLast)
{
/* Process one BB */
// pbb = m_dfsLast[i];
if (not pbb->valid())
continue;
pbb->findBBExps( this->localId, this);
/* Store number of high-level icodes in current basic block */
pbb->numHlIcodes = numHlIcodes;
} }
} }
@ -1126,25 +1140,21 @@ void Function::dataFlow(std::bitset<32> &_liveOut)
if(isAL && isAH) if(isAL && isAH)
{ {
isAx = true; isAx = true;
printf("**************************************************************************** dataFlow Join discovered Ax\n");
isAH=isAL=false; isAH=isAL=false;
} }
if(isDL && isDH) if(isDL && isDH)
{ {
isDx = true; isDx = true;
printf("**************************************************************************** dataFlow Join discovered Dx\n");
isDH=isDL=false; isDH=isDL=false;
} }
if(isBL && isBH) if(isBL && isBH)
{ {
isBx = true; isBx = true;
printf("**************************************************************************** dataFlow Join discovered Dx\n");
isBH=isBL=false; isBH=isBL=false;
} }
if(isCL && isCH) if(isCL && isCH)
{ {
isCx = true; isCx = true;
printf("**************************************************************************** dataFlow Join discovered Dx\n");
isCH=isCL=false; isCH=isCL=false;
} }
@ -1173,7 +1183,6 @@ void Function::dataFlow(std::bitset<32> &_liveOut)
} }
else if(isAL||isBL||isCL||isDL) else if(isAL||isBL||isCL||isDL)
{ {
printf("**************************************************************************** AL/DL return \n");
retVal.type = TYPE_BYTE_SIGN; retVal.type = TYPE_BYTE_SIGN;
retVal.loc = REG_FRAME; retVal.loc = REG_FRAME;
if (isAL) if (isAL)

View File

@ -30,23 +30,26 @@ void Function::createCFG()
* 6) End of procedure * 6) End of procedure
*/ */
int i; int i;
int ip, start; int ip;
BB * psBB; BB * psBB;
BB * pBB; BB * pBB;
iICODE pIcode = Icode.begin(); iICODE pIcode = Icode.begin();
iICODE iStart = Icode.begin();
stats.numBBbef = stats.numBBaft = 0; stats.numBBbef = stats.numBBaft = 0;
for (ip = start = 0; pIcode!=Icode.end(); ip++, pIcode++) for (; pIcode!=Icode.end(); ++pIcode)
{ {
iICODE nextIcode = ++iICODE(pIcode);
LLInst *ll = pIcode->ll(); LLInst *ll = pIcode->ll();
/* Stick a NOWHERE_NODE on the end if we terminate /* Stick a NOWHERE_NODE on the end if we terminate
* with anything other than a ret, jump or terminate */ * with anything other than a ret, jump or terminate */
if (ip + 1 == Icode.size() and if (nextIcode == Icode.end() and
(not ll->testFlags(TERMINATES)) and (not ll->testFlags(TERMINATES)) and
(not ll->match(iJMP)) and (not ll->match(iJMPF)) and (not ll->match(iJMP)) and (not ll->match(iJMPF)) and
(not ll->match(iRET)) and (not ll->match(iRETF))) (not ll->match(iRET)) and (not ll->match(iRETF)))
{ {
pBB=BB::Create(start, ip, NOWHERE_NODE, 0, this); //pBB=BB::Create(start, ip, NOWHERE_NODE, 0, this);
pBB=BB::Create(iStart, pIcode, NOWHERE_NODE, 0, this);
} }
/* Only process icodes that have valid instructions */ /* Only process icodes that have valid instructions */
@ -58,10 +61,11 @@ void Function::createCFG()
case iJE: case iJNE: case iJS: case iJNS: case iJE: case iJNE: case iJS: case iJNS:
case iJO: case iJNO: case iJP: case iJNP: case iJO: case iJNO: case iJP: case iJNP:
case iJCXZ: case iJCXZ:
pBB = BB::Create(start, ip, TWO_BRANCH, 2, this); pBB = BB::Create(iStart, pIcode, TWO_BRANCH, 2, this);
CondJumps: CondJumps:
start = ip + 1; //start = ip + 1;
pBB->edges[0].ip = (uint32_t)start; iStart = ++iICODE(pIcode);
pBB->edges[0].ip = (uint32_t)iStart->loc_ip;
/* This is for jumps off into nowhere */ /* This is for jumps off into nowhere */
if ( ll->testFlags(NO_LABEL) ) if ( ll->testFlags(NO_LABEL) )
{ {
@ -72,25 +76,29 @@ CondJumps:
break; break;
case iLOOP: case iLOOPE: case iLOOPNE: case iLOOP: case iLOOPE: case iLOOPNE:
pBB = BB::Create(start, ip, LOOP_NODE, 2, this); //pBB = BB::Create(start, ip, LOOP_NODE, 2, this);
pBB = BB::Create(iStart, pIcode, LOOP_NODE, 2, this);
goto CondJumps; goto CondJumps;
case iJMPF: case iJMP: case iJMPF: case iJMP:
if (ll->testFlags(SWITCH)) if (ll->testFlags(SWITCH))
{ {
pBB = BB::Create(start, ip, MULTI_BRANCH, ll->caseTbl.numEntries, this); //pBB = BB::Create(start, ip, MULTI_BRANCH, ll->caseTbl.numEntries, this);
pBB = BB::Create(iStart, pIcode, MULTI_BRANCH, ll->caseTbl.numEntries, this);
for (i = 0; i < ll->caseTbl.numEntries; i++) for (i = 0; i < ll->caseTbl.numEntries; i++)
pBB->edges[i].ip = ll->caseTbl.entries[i]; pBB->edges[i].ip = ll->caseTbl.entries[i];
hasCase = true; hasCase = true;
} }
else if ((ll->getFlag() & (I | NO_LABEL)) == I) //TODO: WHY NO_LABEL TESTIT else if ((ll->getFlag() & (I | NO_LABEL)) == I) //TODO: WHY NO_LABEL TESTIT
{ {
pBB = BB::Create(start, ip, ONE_BRANCH, 1, this); //pBB = BB::Create(start, ip, ONE_BRANCH, 1, this);
pBB = BB::Create(iStart, pIcode, ONE_BRANCH, 1, this);
pBB->edges[0].ip = ll->src.op(); pBB->edges[0].ip = ll->src.op();
} }
else else
BB::Create(start, ip, NOWHERE_NODE, 0, this); BB::Create(iStart, pIcode, NOWHERE_NODE, 0, this);
start = ip + 1; iStart = ++iICODE(pIcode);
break; break;
case iCALLF: case iCALL: case iCALLF: case iCALL:
@ -100,16 +108,17 @@ CondJumps:
i = ((p->flg) & TERMINATES) ? 0 : 1; i = ((p->flg) & TERMINATES) ? 0 : 1;
else else
i = 1; i = 1;
pBB = BB::Create(start, ip, CALL_NODE, i, this); pBB = BB::Create(iStart, pIcode, CALL_NODE, i, this);
start = ip + 1; iStart = ++iICODE(pIcode);//start = ip + 1;
if (i) if (i)
pBB->edges[0].ip = (uint32_t)start; pBB->edges[0].ip = iStart->loc_ip;//(uint32_t)start;
} }
break; break;
case iRET: case iRETF: case iRET: case iRETF:
BB::Create(start, ip, RETURN_NODE, 0, this); //BB::Create(start, ip, RETURN_NODE, 0, this);
start = ip + 1; BB::Create(iStart, pIcode, RETURN_NODE, 0, this);
iStart = ++iICODE(pIcode);
break; break;
default: default:
@ -117,18 +126,20 @@ CondJumps:
iICODE next1=++iICODE(pIcode); iICODE next1=++iICODE(pIcode);
if ( ll->testFlags(TERMINATES) ) if ( ll->testFlags(TERMINATES) )
{ {
pBB = BB::Create(start, ip, TERMINATE_NODE, 0, this); pBB = BB::Create(iStart, pIcode, TERMINATE_NODE, 0, this);
start = ip + 1; //pBB = BB::Create(start, ip, TERMINATE_NODE, 0, this);
iStart = ++iICODE(pIcode); // start = ip + 1;
} }
/* Check for a fall through */ /* Check for a fall through */
else if (next1 != Icode.end()) else if (next1 != Icode.end())
{ {
assert(next1->loc_ip==ip+1);
if (next1->ll()->testFlags(TARGET | CASE)) if (next1->ll()->testFlags(TARGET | CASE))
{ {
pBB = BB::Create(start, ip, FALL_NODE, 1, this); //pBB = BB::Create(start, ip, FALL_NODE, 1, this);
start = ip + 1; pBB = BB::Create(iStart, pIcode, FALL_NODE, 1, this);
pBB->edges[0].ip = (uint32_t)start; iStart = ++iICODE(pIcode); // start = ip + 1;
pBB->addOutEdge(iStart->loc_ip);
pBB->edges[0].ip = iStart->loc_ip;//(uint32_t)start;
} }
} }
break; break;
@ -142,7 +153,7 @@ CondJumps:
pBB = *iter; pBB = *iter;
for (size_t edeg_idx = 0; edeg_idx < pBB->edges.size(); edeg_idx++) for (size_t edeg_idx = 0; edeg_idx < pBB->edges.size(); edeg_idx++)
{ {
ip = pBB->edges[edeg_idx].ip; uint32_t ip = pBB->edges[edeg_idx].ip;
if (ip >= SYNTHESIZED_MIN) if (ip >= SYNTHESIZED_MIN)
{ {
fatalError (INVALID_SYNTHETIC_BB); fatalError (INVALID_SYNTHETIC_BB);
@ -273,13 +284,13 @@ void Function::compressCFG()
***************************************************************************/ ***************************************************************************/
BB *BB::rmJMP(int marker, BB * pBB) BB *BB::rmJMP(int marker, BB * pBB)
{ {
marker += DFS_JMP; marker += (int)DFS_JMP;
while (pBB->nodeType == ONE_BRANCH && pBB->size() == 1) while (pBB->nodeType == ONE_BRANCH && pBB->size() == 1)
{ {
if (pBB->traversed != marker) if (pBB->traversed != marker)
{ {
pBB->traversed = marker; pBB->traversed = (eDFS)marker;
pBB->inEdges.pop_back(); pBB->inEdges.pop_back();
if (not pBB->inEdges.empty()) if (not pBB->inEdges.empty())
{ {
@ -347,15 +358,14 @@ void BB::mergeFallThrough( CIcodeRec &Icode)
back().ll()->setFlags(NO_CODE); back().ll()->setFlags(NO_CODE);
back().invalidate(); back().invalidate();
nodeType = FALL_NODE; nodeType = FALL_NODE;
range_end--; //instructions.advance_end(-1); //TODO: causes creation of empty BB
} }
/* If there's no other edges into child can merge */ /* If there's no other edges into child can merge */
if (pChild->inEdges.size() != 1) if (pChild->inEdges.size() != 1)
break; break;
nodeType = pChild->nodeType; nodeType = pChild->nodeType;
range_end = pChild->range_end; instructions = boost::make_iterator_range(begin(),pChild->end());
pChild->front().ll()->clrFlags(TARGET); pChild->front().ll()->clrFlags(TARGET);
edges.swap(pChild->edges); edges.swap(pChild->edges);

View File

@ -36,6 +36,14 @@ void CIcodeRec::SetInBB(int start, int _end, BB *pnewBB)
} }
} }
void CIcodeRec::SetInBB(rCODE &rang, BB *pnewBB)
{
for(ICODE &ic : rang)
{
ic.inBB = pnewBB;
}
}
/* labelSrchRepl - Searches the icodes for instruction with label = target, and /* labelSrchRepl - Searches the icodes for instruction with label = target, and
replaces *pIndex with an icode index */ replaces *pIndex with an icode index */
bool CIcodeRec::labelSrch(uint32_t target, uint32_t &pIndex) bool CIcodeRec::labelSrch(uint32_t target, uint32_t &pIndex)

View File

@ -176,7 +176,12 @@ int LOCAL_ID::newLongReg(hlType t, eReg regH, eReg regL, iICODE ix_)
id_arr[idx].id.longId.l = regL; id_arr[idx].id.longId.l = regL;
return (idx); return (idx);
} }
/* Returns an identifier conditional expression node of type TYPE_LONG or
* TYPE_WORD_SIGN */
COND_EXPR * LOCAL_ID::createId(const ID *retVal, iICODE ix_)
{
return COND_EXPR::idID(retVal,this,ix_);
}
/* Checks if the entry exists in the locSym, if so, returns the idx to this /* Checks if the entry exists in the locSym, if so, returns the idx to this
* entry; otherwise creates a new global identifier node of type * entry; otherwise creates a new global identifier node of type

View File

@ -92,11 +92,11 @@ void CALL_GRAPH::write()
/* Updates the argument table by including the register(s) (ie. lhs of /* Updates the argument table by including the register(s) (ie. lhs of
* picode) and the actual expression (ie. rhs of picode). * picode) and the actual expression (ie. rhs of picode).
* Note: register(s) are only included once in the table. */ * Note: register(s) are only included once in the table. */
void Function::newRegArg(iICODE picode, iICODE ticode) void LOCAL_ID::newRegArg(iICODE picode, iICODE ticode) const
{ {
COND_EXPR *lhs; COND_EXPR *lhs;
STKFRAME * call_args_stackframe, *target_stackframe; STKFRAME * call_args_stackframe, *target_stackframe;
ID *id; const ID *id;
int tidx; int tidx;
boolT regExist; boolT regExist;
condId type; condId type;
@ -114,7 +114,7 @@ void Function::newRegArg(iICODE picode, iICODE ticode)
type = lhs->expr.ident.idType; type = lhs->expr.ident.idType;
if (type == REGISTER) if (type == REGISTER)
{ {
regL = localId.id_arr[lhs->expr.ident.idNode.regiIdx].id.regi; regL = id_arr[lhs->expr.ident.idNode.regiIdx].id.regi;
if (regL < rAL) if (regL < rAL)
tidx = tproc->localId.newByteWordReg(TYPE_WORD_SIGN, regL); tidx = tproc->localId.newByteWordReg(TYPE_WORD_SIGN, regL);
else else
@ -122,28 +122,28 @@ void Function::newRegArg(iICODE picode, iICODE ticode)
} }
else if (type == LONG_VAR) else if (type == LONG_VAR)
{ {
regL = localId.id_arr[lhs->expr.ident.idNode.longIdx].id.longId.l; int longIdx = lhs->expr.ident.idNode.longIdx;
regH = localId.id_arr[lhs->expr.ident.idNode.longIdx].id.longId.h; regL = id_arr[longIdx].id.longId.l;
regH = id_arr[longIdx].id.longId.h;
tidx = tproc->localId.newLongReg(TYPE_LONG_SIGN, regH, regL, tproc->Icode.begin() /*0*/); tidx = tproc->localId.newLongReg(TYPE_LONG_SIGN, regH, regL, tproc->Icode.begin() /*0*/);
//tidx = tproc->localId.newLongReg(TYPE_LONG_SIGN, regH, regL, Icode.begin() /*0*/);
} }
/* Check if register argument already on the formal argument list */ /* Check if register argument already on the formal argument list */
regExist = false; regExist = false;
for(STKSYM &tgt_sym : *target_stackframe) for(STKSYM &tgt_sym : *target_stackframe)
{ {
if( tgt_sym.regs == NULL ) // both REGISTER and LONG_VAR require this precondition
continue;
if (type == REGISTER) if (type == REGISTER)
{ {
if ((tgt_sym.regs != NULL) && if ( tgt_sym.regs->expr.ident.idNode.regiIdx == tidx )
(tgt_sym.regs->expr.ident.idNode.regiIdx == tidx))
{ {
regExist = true; regExist = true;
} }
} }
else if (type == LONG_VAR) else if (type == LONG_VAR)
{ {
if ((tgt_sym.regs != NULL) && if ( tgt_sym.regs->expr.ident.idNode.longIdx == tidx )
(tgt_sym.regs->expr.ident.idNode.longIdx == tidx))
{ {
regExist = true; regExist = true;
} }
@ -192,7 +192,7 @@ void Function::newRegArg(iICODE picode, iICODE ticode)
/* Mask off high and low register(s) in picode */ /* Mask off high and low register(s) in picode */
switch (type) { switch (type) {
case REGISTER: case REGISTER:
id = &localId.id_arr[lhs->expr.ident.idNode.regiIdx]; id = &id_arr[lhs->expr.ident.idNode.regiIdx];
picode->du.def &= maskDuReg[id->id.regi]; picode->du.def &= maskDuReg[id->id.regi];
if (id->id.regi < rAL) if (id->id.regi < rAL)
newsym.type = TYPE_WORD_SIGN; newsym.type = TYPE_WORD_SIGN;
@ -200,7 +200,7 @@ void Function::newRegArg(iICODE picode, iICODE ticode)
newsym.type = TYPE_BYTE_SIGN; newsym.type = TYPE_BYTE_SIGN;
break; break;
case LONG_VAR: case LONG_VAR:
id = &localId.id_arr[lhs->expr.ident.idNode.longIdx]; id = &id_arr[lhs->expr.ident.idNode.longIdx];
picode->du.def &= maskDuReg[id->id.longId.h]; picode->du.def &= maskDuReg[id->id.longId.h];
picode->du.def &= maskDuReg[id->id.longId.l]; picode->du.def &= maskDuReg[id->id.longId.l];
newsym.type = TYPE_LONG_SIGN; newsym.type = TYPE_LONG_SIGN;
@ -252,6 +252,11 @@ void CallType::placeStkArg (COND_EXPR *exp, int pos)
(*args)[pos].setArgName(pos); (*args)[pos].setArgName(pos);
} }
COND_EXPR *CallType::toId()
{
return COND_EXPR::idFunc( proc, args);
}
/* Checks to determine whether the expression (actual argument) has the /* Checks to determine whether the expression (actual argument) has the
* same type as the given type (from the procedure's formal list). If not, * same type as the given type (from the procedure's formal list). If not,