Split COND_EXPR into Unary/Binary/AstIdent subclasses

This commit is contained in:
Artur K 2012-07-16 19:31:29 +02:00
parent ca129c5177
commit c1eb8df114
27 changed files with 1165 additions and 1077 deletions

View File

@ -2,7 +2,7 @@ PROJECT(dcc_original)
CMAKE_MINIMUM_REQUIRED(VERSION 2.8) CMAKE_MINIMUM_REQUIRED(VERSION 2.8)
OPTION(dcc_build_tests "Enable unit tests." OFF) OPTION(dcc_build_tests "Enable unit tests." OFF)
#SET(LIBRARY_OUTPUT_PATH ${PROJECT_SOURCE_DIR})
ADD_DEFINITIONS(-D_CRT_SECURE_NO_WARNINGS -D__UNIX__ -D__STDC_LIMIT_MACROS -D__STDC_CONSTANT_MACROS -D__STDC_FORMAT_MACROS) ADD_DEFINITIONS(-D_CRT_SECURE_NO_WARNINGS -D__UNIX__ -D__STDC_LIMIT_MACROS -D__STDC_CONSTANT_MACROS -D__STDC_FORMAT_MACROS)
IF(CMAKE_BUILD_TOOL MATCHES "(msdev|devenv|nmake)") IF(CMAKE_BUILD_TOOL MATCHES "(msdev|devenv|nmake)")
ADD_DEFINITIONS(-D_CRT_SECURE_NO_WARNINGS -D__UNIX__ -D_CRT_NONSTDC_NO_DEPRECATE) ADD_DEFINITIONS(-D_CRT_SECURE_NO_WARNINGS -D__UNIX__ -D_CRT_NONSTDC_NO_DEPRECATE)
@ -14,6 +14,7 @@ ELSE()
ENDIF() ENDIF()
SET(CMAKE_MODULE_PATH ${PROJECT_SOURCE_DIR}/CMakeScripts;${CMAKE_MODULE_PATH}) SET(CMAKE_MODULE_PATH ${PROJECT_SOURCE_DIR}/CMakeScripts;${CMAKE_MODULE_PATH})
SET(EXECUTABLE_OUTPUT_PATH ${PROJECT_SOURCE_DIR})
include(cotire) include(cotire)
FIND_PACKAGE(LLVM) FIND_PACKAGE(LLVM)
FIND_PACKAGE(Boost) FIND_PACKAGE(Boost)

View File

@ -216,6 +216,7 @@ enum condNodeType
{ {
UNKNOWN_OP=0, UNKNOWN_OP=0,
BOOLEAN_OP, /* condOps */ BOOLEAN_OP, /* condOps */
NEGATION, /* not (2's complement) */ NEGATION, /* not (2's complement) */
ADDRESSOF, /* addressOf (&) */ ADDRESSOF, /* addressOf (&) */
DEREFERENCE, /* contents of (*) */ DEREFERENCE, /* contents of (*) */

View File

@ -22,7 +22,7 @@ static const int operandSize=20;
static const condOp condOpJCond[12] = {LESS, LESS_EQUAL, GREATER_EQUAL, GREATER, static const condOp condOpJCond[12] = {LESS, LESS_EQUAL, GREATER_EQUAL, GREATER,
EQUAL, NOT_EQUAL, LESS, GREATER_EQUAL, EQUAL, NOT_EQUAL, LESS, GREATER_EQUAL,
LESS_EQUAL, GREATER, GREATER_EQUAL, LESS}; LESS_EQUAL, GREATER, GREATER_EQUAL, LESS};
struct AstIdent;
struct Function; struct Function;
struct STKFRAME; struct STKFRAME;
struct LOCAL_ID; struct LOCAL_ID;
@ -36,129 +36,48 @@ typedef boost::iterator_range<iICODE> rICODE;
/* Expression data type */ /* Expression data type */
struct COND_EXPR struct COND_EXPR
{ {
protected:
struct /* for BOOLEAN_OP */
{
condOp op;
COND_EXPR *lhs;
COND_EXPR *rhs;
} boolExpr;
public: public:
condNodeType m_type; /* Conditional Expression Node Type */ condNodeType m_type; /* Conditional Expression Node Type */
union _exprNode { /* Different cond expr nodes */
COND_EXPR *unaryExp; /* for NEGATION,ADDRESSOF,DEREFERENCE*/
IDENTTYPE ident; /* for IDENTIFIER */
} expr;
COND_EXPR *lhs()
{
assert(m_type==BOOLEAN_OP);
return boolExpr.lhs;
}
const COND_EXPR *lhs() const
{
assert(m_type==BOOLEAN_OP);
return boolExpr.lhs;
}
COND_EXPR *rhs()
{
assert(m_type==BOOLEAN_OP);
return boolExpr.rhs;
}
const COND_EXPR *rhs() const
{
assert(m_type==BOOLEAN_OP);
return boolExpr.rhs;
}
condOp op() const { return boolExpr.op;}
public: public:
static COND_EXPR * idRegIdx(int idx, regType reg_type); static bool insertSubTreeLongReg(COND_EXPR *exp, COND_EXPR *&tree, int longIdx);
static COND_EXPR * idKte(uint32_t kte, uint8_t size);
static COND_EXPR * idLoc(int off, LOCAL_ID *localId);
static COND_EXPR * idReg(eReg regi, uint32_t icodeFlg, LOCAL_ID *locsym);
static COND_EXPR * idLongIdx(int idx);
static COND_EXPR * idOther(eReg seg, eReg regi, int16_t off);
static COND_EXPR * idParam(int off, const STKFRAME *argSymtab);
static COND_EXPR * unary(condNodeType t, COND_EXPR *sub_expr);
static COND_EXPR * idLong(LOCAL_ID *localId, opLoc sd, iICODE pIcode, hlFirst f, iICODE ix, operDu du, LLInst &atOffset);
static COND_EXPR * idFunc(Function *pproc, STKFRAME *args);
static COND_EXPR * idID(const ID *retVal, LOCAL_ID *locsym, iICODE ix_);
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 bool insertSubTreeLongReg(COND_EXPR *exp, COND_EXPR **tree, int longIdx);
static bool insertSubTreeReg(COND_EXPR *&tree, COND_EXPR *_expr, eReg regi, const LOCAL_ID *locsym); static bool insertSubTreeReg(COND_EXPR *&tree, COND_EXPR *_expr, eReg regi, const LOCAL_ID *locsym);
static bool insertSubTreeReg(AstIdent *&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();
void changeBoolOp(condOp newOp);
COND_EXPR(const COND_EXPR &other)
{
m_type=other.m_type;
expr=other.expr;
boolExpr=other.boolExpr;
}
COND_EXPR(condNodeType t=UNKNOWN_OP) : m_type(t) COND_EXPR(condNodeType t=UNKNOWN_OP) : m_type(t)
{ {
memset(&expr,0,sizeof(_exprNode));
memset(&boolExpr,0,sizeof(boolExpr));
} }
virtual ~COND_EXPR() {} virtual ~COND_EXPR();
public: public:
virtual COND_EXPR *inverse() const; // return new COND_EXPR that is invarse of this virtual std::string walkCondExpr (Function * pProc, int* numLoc) const=0;
virtual bool xClear(rICODE range_to_check, iICODE lastBBinst, const LOCAL_ID &locId); virtual COND_EXPR *inverse() const=0; // return new COND_EXPR that is invarse of this
virtual COND_EXPR *insertSubTreeReg(COND_EXPR *_expr, eReg regi, const LOCAL_ID *locsym); virtual bool xClear(rICODE range_to_check, iICODE lastBBinst, const LOCAL_ID &locId)=0;
virtual COND_EXPR *insertSubTreeLongReg(COND_EXPR *_expr, int longIdx); virtual COND_EXPR *insertSubTreeReg(COND_EXPR *_expr, eReg regi, const LOCAL_ID *locsym)=0;
virtual COND_EXPR *insertSubTreeLongReg(COND_EXPR *_expr, int longIdx)=0;
virtual hlType expType(Function *pproc) const; virtual hlType expType(Function *pproc) const;
}; virtual int hlTypeSize(Function *pproc) const=0;
struct BinaryOperator : public COND_EXPR virtual void performLongRemoval(eReg regi, LOCAL_ID *locId) {}
{
condOp m_op;
COND_EXPR *m_lhs;
COND_EXPR *m_rhs;
BinaryOperator(condOp o)
{
m_op = o;
m_lhs=m_rhs=nullptr;
}
static BinaryOperator *Create(condOp o,COND_EXPR *l,COND_EXPR *r);
static BinaryOperator *CreateAdd(COND_EXPR *l,COND_EXPR *r);
virtual COND_EXPR *inverse() const;
virtual COND_EXPR *clone() const;
virtual bool xClear(rICODE range_to_check, iICODE lastBBinst, const LOCAL_ID &locs);
virtual COND_EXPR *insertSubTreeReg(COND_EXPR *_expr, eReg regi, const LOCAL_ID *locsym);
virtual COND_EXPR *insertSubTreeLongReg(COND_EXPR *_expr, int longIdx);
COND_EXPR *lhs()
{
assert(m_type==BOOLEAN_OP);
return m_lhs;
}
const COND_EXPR *lhs() const
{
assert(m_type==BOOLEAN_OP);
return m_lhs;
}
COND_EXPR *rhs()
{
assert(m_type==BOOLEAN_OP);
return m_rhs;
}
const COND_EXPR *rhs() const
{
assert(m_type==BOOLEAN_OP);
return m_rhs;
}
condOp op() const { return m_op;}
/* Changes the boolean conditional operator at the root of this expression */
void op(condOp o) { m_op=o;}
}; };
struct UnaryOperator : public COND_EXPR struct UnaryOperator : public COND_EXPR
{ {
condOp op; UnaryOperator(condNodeType t=UNKNOWN_OP) : COND_EXPR(t),unaryExp(nullptr) {}
COND_EXPR *unaryExp; COND_EXPR *unaryExp;
virtual COND_EXPR *inverse() const; virtual COND_EXPR *inverse() const
virtual COND_EXPR *clone() const; {
if (m_type == NEGATION) //TODO: memleak here
{
return unaryExp->clone();
}
return this->clone();
}
virtual COND_EXPR *clone() const
{
UnaryOperator *newExp = new UnaryOperator(*this);
newExp->unaryExp = unaryExp->clone();
return newExp;
}
virtual bool xClear(rICODE range_to_check, iICODE lastBBinst, const LOCAL_ID &locs); virtual bool xClear(rICODE range_to_check, iICODE lastBBinst, const LOCAL_ID &locs);
static UnaryOperator *Create(condNodeType t, COND_EXPR *sub_expr) static UnaryOperator *Create(condNodeType t, COND_EXPR *sub_expr)
{ {
@ -167,11 +86,135 @@ struct UnaryOperator : public COND_EXPR
newExp->unaryExp = sub_expr; newExp->unaryExp = sub_expr;
return (newExp); return (newExp);
} }
~UnaryOperator()
{
delete unaryExp;
unaryExp=nullptr;
}
public:
int hlTypeSize(Function *pproc) const;
virtual std::string walkCondExpr(Function *pProc, int *numLoc) const;
virtual COND_EXPR *insertSubTreeReg(COND_EXPR *_expr, eReg regi, const LOCAL_ID *locsym);
virtual hlType expType(Function *pproc) const;
virtual COND_EXPR *insertSubTreeLongReg(COND_EXPR *_expr, int longIdx);
}; };
struct GlobalVariable : public COND_EXPR struct BinaryOperator : public COND_EXPR
{ {
static COND_EXPR *Create(int16_t segValue, int16_t off); condOp m_op;
COND_EXPR *m_lhs;
COND_EXPR *m_rhs;
BinaryOperator(condOp o) : COND_EXPR(BOOLEAN_OP)
{
m_op = o;
m_lhs=m_rhs=nullptr;
}
BinaryOperator(condOp o,COND_EXPR *l,COND_EXPR *r) : COND_EXPR(BOOLEAN_OP)
{
m_op = o;
m_lhs=l;
m_rhs=r;
}
~BinaryOperator()
{
assert(m_lhs!=m_rhs || m_lhs==nullptr);
delete m_lhs;
delete m_rhs;
}
static BinaryOperator *Create(condOp o,COND_EXPR *l,COND_EXPR *r)
{
BinaryOperator *res = new BinaryOperator(o);
res->m_lhs = l;
res->m_rhs = r;
return res;
}
static BinaryOperator *LogicAnd(COND_EXPR *l,COND_EXPR *r)
{
return new BinaryOperator(DBL_AND,l,r);
}
static BinaryOperator *And(COND_EXPR *l,COND_EXPR *r)
{
return new BinaryOperator(AND,l,r);
}
static BinaryOperator *Or(COND_EXPR *l,COND_EXPR *r)
{
return new BinaryOperator(OR,l,r);
}
static BinaryOperator *LogicOr(COND_EXPR *l,COND_EXPR *r)
{
return new BinaryOperator(DBL_OR,l,r);
}
static BinaryOperator *CreateAdd(COND_EXPR *l,COND_EXPR *r);
void changeBoolOp(condOp newOp);
virtual COND_EXPR *inverse() const;
virtual COND_EXPR *clone() const;
virtual bool xClear(rICODE range_to_check, iICODE lastBBinst, const LOCAL_ID &locs);
virtual COND_EXPR *insertSubTreeReg(COND_EXPR *_expr, eReg regi, const LOCAL_ID *locsym);
virtual COND_EXPR *insertSubTreeLongReg(COND_EXPR *_expr, int longIdx);
const COND_EXPR *lhs() const
{
return const_cast<const COND_EXPR *>(const_cast<BinaryOperator *>(this)->lhs());
}
const COND_EXPR *rhs() const
{
return const_cast<const COND_EXPR *>(const_cast<BinaryOperator *>(this)->rhs());
}
COND_EXPR *lhs()
{
assert(m_type==BOOLEAN_OP);
return m_lhs;
}
COND_EXPR *rhs()
{
assert(m_type==BOOLEAN_OP);
return m_rhs;
}
condOp op() const { return m_op;}
/* Changes the boolean conditional operator at the root of this expression */
void op(condOp o) { m_op=o;}
std::string walkCondExpr (Function * pProc, int* numLoc) const;
public:
hlType expType(Function *pproc) const;
int hlTypeSize(Function *pproc) const;
};
struct AstIdent : public UnaryOperator
{
AstIdent() : UnaryOperator(IDENTIFIER)
{
memset(&ident,0,sizeof(ident));
}
virtual COND_EXPR *clone() const
{
return new AstIdent(*this);
}
IDENTTYPE ident; /* for IDENTIFIER */
static AstIdent * RegIdx(int idx, regType reg_type);
static AstIdent * Kte(uint32_t kte, uint8_t size);
static AstIdent * Loc(int off, LOCAL_ID *localId);
static AstIdent * Reg(eReg regi, uint32_t icodeFlg, LOCAL_ID *locsym);
static AstIdent * LongIdx(int idx);
static AstIdent * Other(eReg seg, eReg regi, int16_t off);
static AstIdent * idParam(int off, const STKFRAME *argSymtab);
static AstIdent * idLong(LOCAL_ID *localId, opLoc sd, iICODE pIcode, hlFirst f, iICODE ix, operDu du, LLInst &atOffset);
static AstIdent * idFunc(Function *pproc, STKFRAME *args);
static AstIdent * idID(const ID *retVal, LOCAL_ID *locsym, iICODE ix_);
static COND_EXPR * id(const LLInst &ll_insn, opLoc sd, Function *pProc, iICODE ix_, ICODE &duIcode, operDu du);
virtual int hlTypeSize(Function *pproc) const;
virtual hlType expType(Function *pproc) const;
virtual void performLongRemoval(eReg regi, LOCAL_ID *locId);
virtual std::string walkCondExpr(Function *pProc, int *numLoc) const;
virtual COND_EXPR *insertSubTreeReg(COND_EXPR *_expr, eReg regi, const LOCAL_ID *locsym);
virtual COND_EXPR *insertSubTreeLongReg(COND_EXPR *_expr, int longIdx);
virtual bool xClear(rICODE range_to_check, iICODE lastBBinst, const LOCAL_ID &locId);
protected:
eReg otherLongRegi (eReg regi, int idx, LOCAL_ID *locTbl);
};
struct GlobalVariable : public AstIdent
{
static AstIdent *Create(int16_t segValue, int16_t off);
}; };
struct Constant : public COND_EXPR struct Constant : public COND_EXPR
{}; {};

View File

@ -128,12 +128,6 @@ bool LibCheck(Function &p); /* chklib.c */
boolT insertCallGraph (CALL_GRAPH *, ilFunction, ilFunction); boolT insertCallGraph (CALL_GRAPH *, ilFunction, ilFunction);
void adjustActArgType (COND_EXPR *, hlType, Function *); void adjustActArgType (COND_EXPR *, hlType, Function *);
/* Exported functions from ast.c */
std::string walkCondExpr (const COND_EXPR *exp, Function * pProc, int *);
int hlTypeSize (const COND_EXPR *, Function *);
//hlType expType (const COND_EXPR *, Function *);
/* Exported functions from hlicode.c */ /* Exported functions from hlicode.c */
std::string writeCall (Function *, STKFRAME &, Function *, int *); std::string writeCall (Function *, STKFRAME &, Function *, int *);
char *writeJcond (const HLTYPE &, Function *, int *); char *writeJcond (const HLTYPE &, Function *, int *);

View File

@ -84,11 +84,12 @@ struct DU
struct COND_EXPR; struct COND_EXPR;
struct AstIdent;
struct HlTypeSupport struct HlTypeSupport
{ {
//hlIcode opcode; /* hlIcode opcode */ //hlIcode opcode; /* hlIcode opcode */
virtual bool removeRegFromLong(eReg regi, LOCAL_ID *locId)=0; virtual bool removeRegFromLong(eReg regi, LOCAL_ID *locId)=0;
virtual std::string writeOut(Function *pProc, int *numLoc)=0; virtual std::string writeOut(Function *pProc, int *numLoc) const=0;
protected: protected:
void performLongRemoval (eReg regi, LOCAL_ID *locId, COND_EXPR *tree); void performLongRemoval (eReg regi, LOCAL_ID *locId, COND_EXPR *tree);
}; };
@ -108,7 +109,7 @@ public:
printf("CallType : removeRegFromLong not supproted"); printf("CallType : removeRegFromLong not supproted");
return false; return false;
} }
std::string writeOut(Function *pProc, int *numLoc); std::string writeOut(Function *pProc, int *numLoc) const;
}; };
struct AssignType : public HlTypeSupport struct AssignType : public HlTypeSupport
{ {
@ -116,12 +117,8 @@ struct AssignType : public HlTypeSupport
COND_EXPR *lhs; COND_EXPR *lhs;
COND_EXPR *rhs; COND_EXPR *rhs;
AssignType() : lhs(0),rhs(0) {} AssignType() : lhs(0),rhs(0) {}
bool removeRegFromLong(eReg regi, LOCAL_ID *locId) bool removeRegFromLong(eReg regi, LOCAL_ID *locId);
{ std::string writeOut(Function *pProc, int *numLoc) const;
performLongRemoval(regi,locId,lhs);
return true;
}
std::string writeOut(Function *pProc, int *numLoc);
}; };
struct ExpType : public HlTypeSupport struct ExpType : public HlTypeSupport
{ {
@ -133,7 +130,7 @@ struct ExpType : public HlTypeSupport
performLongRemoval(regi,locId,v); performLongRemoval(regi,locId,v);
return true; return true;
} }
std::string writeOut(Function *pProc, int *numLoc); std::string writeOut(Function *pProc, int *numLoc) const;
}; };
struct HLTYPE struct HLTYPE
@ -145,6 +142,10 @@ public:
AssignType asgn; AssignType asgn;
CallType call; CallType call;
HlTypeSupport *get(); HlTypeSupport *get();
const HlTypeSupport *get() const
{
return const_cast<const HlTypeSupport *>(const_cast<HLTYPE*>(this)->get());
}
void expr(COND_EXPR *e) void expr(COND_EXPR *e)
{ {
@ -162,17 +163,12 @@ public:
opcode=i; opcode=i;
exp.v=e; exp.v=e;
} }
void set(COND_EXPR *l,COND_EXPR *r) void set(COND_EXPR *l,COND_EXPR *r);
{ void setCall(Function *proc);
assert(l);
assert(r);
opcode = HLI_ASSIGN;
assert((asgn.lhs==0) and (asgn.rhs==0)); //prevent memory leaks
asgn.lhs=l;
asgn.rhs=r;
}
HLTYPE(hlIcode op=HLI_INVALID) : opcode(op) HLTYPE(hlIcode op=HLI_INVALID) : opcode(op)
{} {}
// HLTYPE() // help valgrind find uninitialized HLTYPES
// {}
HLTYPE & operator=(const HLTYPE &l) HLTYPE & operator=(const HLTYPE &l)
{ {
exp = l.exp; exp = l.exp;
@ -182,7 +178,7 @@ public:
return *this; return *this;
} }
public: public:
std::string write1HlIcode(Function *pProc, int *numLoc); std::string write1HlIcode(Function *pProc, int *numLoc) const;
void setAsgn(COND_EXPR *lhs, COND_EXPR *rhs); void setAsgn(COND_EXPR *lhs, COND_EXPR *rhs);
} ; } ;
/* LOW_LEVEL icode operand record */ /* LOW_LEVEL icode operand record */
@ -210,7 +206,7 @@ struct LLOperand
{ {
opz=dw; opz=dw;
} }
eReg getReg2() {return regi;} eReg getReg2() const {return regi;}
bool isReg() const; bool isReg() const;
static LLOperand CreateImm2(int64_t Val) static LLOperand CreateImm2(int64_t Val)
{ {
@ -312,7 +308,7 @@ public:
void flops(std::ostringstream &out); void flops(std::ostringstream &out);
bool isJmpInst(); bool isJmpInst();
HLTYPE toHighLevel(COND_EXPR *lhs, COND_EXPR *rhs, Function *func); //HLTYPE toHighLevel(COND_EXPR *lhs, COND_EXPR *rhs, Function *func);
HLTYPE createCall(); HLTYPE createCall();
LLInst(ICODE *container) : flg(0),codeIdx(0),numBytes(0),m_link(container) LLInst(ICODE *container) : flg(0),codeIdx(0),numBytes(0),m_link(container)
{ {
@ -450,8 +446,16 @@ public:
LLInst * ll() { return &m_ll;} LLInst * ll() { return &m_ll;}
const LLInst * ll() const { return &m_ll;} const LLInst * ll() const { return &m_ll;}
HLTYPE * hl() { return &m_hl;} HLTYPE * hlU() {
const HLTYPE * hl() const { return &m_hl;} // assert(type==HIGH_LEVEL);
// assert(m_hl.opcode!=HLI_INVALID);
return &m_hl;
}
const HLTYPE * hl() const {
// assert(type==HIGH_LEVEL);
// assert(m_hl.opcode!=HLI_INVALID);
return &m_hl;
}
void hl(const HLTYPE &v) { m_hl=v;} void hl(const HLTYPE &v) { m_hl=v;}
void setRegDU(eReg regi, operDu du_in); void setRegDU(eReg regi, operDu du_in);
@ -464,7 +468,7 @@ public:
void setAsgn(COND_EXPR *lhs, COND_EXPR *rhs) void setAsgn(COND_EXPR *lhs, COND_EXPR *rhs)
{ {
type=HIGH_LEVEL; type=HIGH_LEVEL;
hl()->setAsgn(lhs,rhs); hlU()->setAsgn(lhs,rhs);
} }
void setUnary(hlIcode op, COND_EXPR *_exp); void setUnary(hlIcode op, COND_EXPR *_exp);
void setJCond(COND_EXPR *cexp); void setJCond(COND_EXPR *cexp);
@ -478,7 +482,7 @@ public:
void checkHlCall(); void checkHlCall();
bool newStkArg(COND_EXPR *exp, llIcode opcode, Function *pproc) bool newStkArg(COND_EXPR *exp, llIcode opcode, Function *pproc)
{ {
return hl()->call.newStkArg(exp,opcode,pproc); return hlU()->call.newStkArg(exp,opcode,pproc);
} }
ICODE() : m_ll(this),Parent(0),invalid(false),type(NOT_SCANNED),loc_ip(0) ICODE() : m_ll(this),Parent(0),invalid(false),type(NOT_SCANNED),loc_ip(0)
{ {

View File

@ -19,6 +19,7 @@
// 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 COND_EXPR;
struct AstIdent;
struct ICODE; struct ICODE;
struct LLInst; struct LLInst;
typedef std::list<ICODE>::iterator iICODE; typedef std::list<ICODE>::iterator iICODE;
@ -132,7 +133,7 @@ public:
void newRegArg(iICODE picode, iICODE ticode) const; void newRegArg(iICODE picode, iICODE ticode) const;
void processTargetIcode(iICODE picode, int &numHlIcodes, iICODE ticode, bool isLong) const; void processTargetIcode(iICODE picode, int &numHlIcodes, iICODE ticode, bool isLong) const;
void forwardSubs(COND_EXPR *lhs, COND_EXPR *rhs, iICODE picode, iICODE ticode, int &numHlIcodes) const; void forwardSubs(COND_EXPR *lhs, COND_EXPR *rhs, iICODE picode, iICODE ticode, int &numHlIcodes) const;
COND_EXPR *createId(const ID *retVal, iICODE ix_); AstIdent *createId(const ID *retVal, iICODE ix_);
}; };

View File

@ -8,6 +8,7 @@
#include "Enums.h" #include "Enums.h"
#include "types.h" #include "types.h"
struct COND_EXPR; struct COND_EXPR;
struct AstIdent;
struct TypeContainer; struct TypeContainer;
/* * * * * * * * * * * * * * * * * */ /* * * * * * * * * * * * * * * * * */
/* Symbol table structs and protos */ /* Symbol table structs and protos */
@ -36,7 +37,7 @@ struct STKSYM : public SymbolCommon
{ {
typedef int16_t tLabel; typedef int16_t tLabel;
COND_EXPR *actual; /* Expression tree of actual parameter */ COND_EXPR *actual; /* Expression tree of actual parameter */
COND_EXPR *regs; /* For register arguments only */ AstIdent *regs; /* For register arguments only */
tLabel label; /* Immediate off from BP (+:args, -:params) */ tLabel label; /* Immediate off from BP (+:args, -:params) */
uint8_t regOff; /* Offset is a register (e.g. SI, DI) */ uint8_t regOff; /* Offset is a register (e.g. SI, DI) */
bool hasMacro; /* This type needs a macro */ bool hasMacro; /* This type needs a macro */
@ -44,7 +45,8 @@ struct STKSYM : public SymbolCommon
bool invalid; /* Boolean: invalid entry in formal arg list*/ bool invalid; /* Boolean: invalid entry in formal arg list*/
STKSYM() STKSYM()
{ {
actual=regs=0; actual=0;
regs=0;
label=0; label=0;
regOff=0; regOff=0;
invalid=hasMacro = false; invalid=hasMacro = false;

View File

@ -1,7 +1,9 @@
/**************************************************************************** /*
***************************************************************************
* dcc project general header * dcc project general header
* (C) Cristina Cifuentes, Mike van Emmerik * (C) Cristina Cifuentes, Mike van Emmerik
****************************************************************************/ ***************************************************************************
*/
#pragma once #pragma once
#include <cassert> #include <cassert>
#include <stdint.h> #include <stdint.h>
@ -22,10 +24,10 @@ typedef unsigned char boolT; /* 8 bits */
#define PATLEN 23 /* Length of proc patterns */ #define PATLEN 23 /* Length of proc patterns */
#define WILD 0xF4 /* The wild byte */ #define WILD 0xF4 /* The wild byte */
/****** MACROS *******/ /* MACROS */
/* Macro reads a LH word from the image regardless of host convention */ // Macro reads a LH word from the image regardless of host convention
/* Returns a 16 bit quantity, e.g. C000 is read into an Int as C000 */ // Returns a 16 bit quantity, e.g. C000 is read into an Int as C000
//#define LH(p) ((int16)((byte *)(p))[0] + ((int16)((byte *)(p))[1] << 8)) //#define LH(p) ((int16)((byte *)(p))[0] + ((int16)((byte *)(p))[1] << 8))
#define LH(p) ((word)((byte *)(p))[0] + ((word)((byte *)(p))[1] << 8)) #define LH(p) ((word)((byte *)(p))[0] + ((word)((byte *)(p))[1] << 8))
@ -53,19 +55,20 @@ struct eDuVal
USE=2, USE=2,
VAL=4 VAL=4
}; };
uint8_t def :1; /* Variable was first defined than used */ uint8_t def :1; //!< Variable was first defined than used
uint8_t use :1; /* Variable was first used than defined */ uint8_t use :1; //!< Variable was first used than defined
uint8_t val :1; /* Variable has an initial value. 2 cases: uint8_t val :1; /* Variable has an initial value. 2 cases:
* 1. When variable is used first (ie. global) 1. When variable is used first (ie. global)
* 2. When a value is moved into the variable 2. When a value is moved into the variable
* for the first time. */ for the first time.
*/
void setFlags(uint16_t x) void setFlags(uint16_t x)
{ {
def = x&DEF; def = x&DEF;
use = x&USE; use = x&USE;
val = x&VAL; val = x&VAL;
} }
bool isUSE_VAL() {return use&&val;} /* Use and Val */ bool isUSE_VAL() {return use&&val;} //Use and Val
}; };
static constexpr const char * hlTypes[13] = { static constexpr const char * hlTypes[13] = {
"", "char", "unsigned char", "int", "unsigned int", "", "char", "unsigned char", "int", "unsigned int",

View File

@ -158,10 +158,10 @@ ICODE* BB::writeLoopHeader(int &indLevel, Function* pProc, int *numLoc, BB *&lat
* the THEN path of the header node */ * the THEN path of the header node */
if (edges[ELSE].BBptr->dfsLastNum == loopFollow) if (edges[ELSE].BBptr->dfsLastNum == loopFollow)
{ {
picode->hl()->replaceExpr(picode->hl()->expr()->inverse()); picode->hlU()->replaceExpr(picode->hl()->expr()->inverse());
} }
{ {
string e=walkCondExpr (picode->hl()->expr(), pProc, numLoc); string e=picode->hl()->expr()->walkCondExpr (pProc, numLoc);
ostr << "\n"<<indentStr(indLevel)<<"while ("<<e<<") {\n"; ostr << "\n"<<indentStr(indLevel)<<"while ("<<e<<") {\n";
} }
picode->invalidate(); picode->invalidate();
@ -262,12 +262,16 @@ void BB::writeCode (int indLevel, Function * pProc , int *numLoc,int _latchNode,
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)
{ {
string e = "//*failed*//";
if (picode->hl()->opcode != HLI_JCOND) if (picode->hl()->opcode != HLI_JCOND)
reportError (REPEAT_FAIL);
{ {
string e=walkCondExpr (picode->hl()->expr(), pProc, numLoc); reportError (REPEAT_FAIL);
cCode.appendCode( "%s} while (%s);\n", indentStr(indLevel),e.c_str());
} }
else
{
e=picode->hl()->expr()->walkCondExpr (pProc, numLoc);
}
cCode.appendCode( "%s} while (%s);\n", indentStr(indLevel),e.c_str());
} }
/* Recurse on the loop follow */ /* Recurse on the loop follow */

File diff suppressed because it is too large Load Diff

View File

@ -6,6 +6,9 @@
****************************************************************************/ ****************************************************************************/
#include <cassert> #include <cassert>
#include <string> #include <string>
#include <boost/range.hpp>
#include <boost/range/adaptors.hpp>
#include <boost/range/algorithm.hpp>
#include "dcc.h" #include "dcc.h"
#include "disassem.h" #include "disassem.h"
@ -15,6 +18,8 @@
#include <string.h> #include <string.h>
#include <stdio.h> #include <stdio.h>
#include "project.h" #include "project.h"
using namespace boost;
using namespace boost::adaptors;
bundle cCode; /* Procedure declaration and code */ bundle cCode; /* Procedure declaration and code */
using namespace std; using namespace std;
@ -215,12 +220,16 @@ void Function::codeGen (std::ostream &fs)
ostr<< "\nvoid "<<name<<" ("; ostr<< "\nvoid "<<name<<" (";
/* Write arguments */ /* Write arguments */
for (size_t i = 0; i < args.size(); i++) struct validArg
{ {
if ( args[i].invalid ) bool operator()(STKSYM &s) { return s.invalid==false;}
continue; };
ostr<<hlTypes[args[i].type]<<" "<<args[i].name; auto valid_args = args | filtered(validArg());
if (i < (args.size() - 1)) int count_valid = std::distance(valid_args.begin(),valid_args.end());
for (STKSYM &arg : valid_args)
{
ostr<<hlTypes[arg.type]<<" "<<arg.name;
if(--count_valid!=0)
ostr<<", "; ostr<<", ";
} }
ostr<<")\n"; ostr<<")\n";

View File

@ -207,14 +207,14 @@ void Function::writeProcComments(std::ostream &ostr)
{ {
psym = &this->args[i]; psym = &this->args[i];
ostr << " * "<<psym->name<<" = "; ostr << " * "<<psym->name<<" = ";
if (psym->regs->expr.ident.idType == REGISTER) if (psym->regs->ident.idType == REGISTER)
{ {
id = &this->localId.id_arr[psym->regs->expr.ident.idNode.regiIdx]; id = &this->localId.id_arr[psym->regs->ident.idNode.regiIdx];
ostr << Machine_X86::regName(id->id.regi); ostr << Machine_X86::regName(id->id.regi);
} }
else /* long register */ else /* long register */
{ {
id = &this->localId.id_arr[psym->regs->expr.ident.idNode.longIdx]; id = &this->localId.id_arr[psym->regs->ident.idNode.longIdx];
ostr << Machine_X86::regName(id->id.longId.h) << ":"; ostr << Machine_X86::regName(id->id.longId.h) << ":";
ostr << Machine_X86::regName(id->id.longId.l); ostr << Machine_X86::regName(id->id.longId.l);
} }

View File

@ -505,14 +505,14 @@ void Function::replaceInEdge(BB* where, BB* which,BB* with)
} }
bool Function::Case_notX_or_Y(BB* pbb, BB* thenBB, BB* elseBB) bool Function::Case_notX_or_Y(BB* pbb, BB* thenBB, BB* elseBB)
{ {
HLTYPE &hl1(*pbb->back().hl()); HLTYPE &hl1(*pbb->back().hlU());
HLTYPE &hl2(*thenBB->back().hl()); HLTYPE &hl2(*thenBB->back().hlU());
BB* obb = elseBB->edges[THEN].BBptr; BB* obb = elseBB->edges[THEN].BBptr;
/* Construct compound DBL_OR expression */ /* Construct compound DBL_OR expression */
hl1.replaceExpr(hl1.expr()->inverse()); hl1.replaceExpr(hl1.expr()->inverse());
hl1.expr(COND_EXPR::boolOp (hl1.expr(), hl2.expr(), DBL_OR)); hl1.expr(BinaryOperator::Create(DBL_OR,hl1.expr(), hl2.expr()));
/* Replace in-edge to obb from e to pbb */ /* Replace in-edge to obb from e to pbb */
replaceInEdge(obb,elseBB,pbb); replaceInEdge(obb,elseBB,pbb);
@ -526,12 +526,12 @@ bool Function::Case_notX_or_Y(BB* pbb, BB* thenBB, BB* elseBB)
} }
bool Function::Case_X_and_Y(BB* pbb, BB* thenBB, BB* elseBB) bool Function::Case_X_and_Y(BB* pbb, BB* thenBB, BB* elseBB)
{ {
HLTYPE &hl1(*pbb->back().hl()); HLTYPE &hl1(*pbb->back().hlU());
HLTYPE &hl2(*thenBB->back().hl()); HLTYPE &hl2(*thenBB->back().hlU());
BB* obb = elseBB->edges[ELSE].BBptr; BB* obb = elseBB->edges[ELSE].BBptr;
/* Construct compound DBL_AND expression */ /* Construct compound DBL_AND expression */
hl1.expr(COND_EXPR::boolOp (hl1.expr(),hl2.expr(), DBL_AND)); hl1.expr(BinaryOperator::Create(DBL_AND,hl1.expr(),hl2.expr()));
/* Replace in-edge to obb from e to pbb */ /* Replace in-edge to obb from e to pbb */
replaceInEdge(obb,elseBB,pbb); replaceInEdge(obb,elseBB,pbb);
@ -545,15 +545,15 @@ bool Function::Case_X_and_Y(BB* pbb, BB* thenBB, BB* elseBB)
bool Function::Case_notX_and_Y(BB* pbb, BB* thenBB, BB* elseBB) bool Function::Case_notX_and_Y(BB* pbb, BB* thenBB, BB* elseBB)
{ {
HLTYPE &hl1(*pbb->back().hl()); HLTYPE &hl1(*pbb->back().hlU());
HLTYPE &hl2(*thenBB->back().hl()); HLTYPE &hl2(*thenBB->back().hlU());
BB* obb = thenBB->edges[ELSE].BBptr; BB* obb = thenBB->edges[ELSE].BBptr;
/* Construct compound DBL_AND expression */ /* Construct compound DBL_AND expression */
hl1.replaceExpr(hl1.expr()->inverse()); hl1.replaceExpr(hl1.expr()->inverse());
hl1.expr(COND_EXPR::boolOp (hl1.expr(), hl2.expr(), DBL_AND)); hl1.expr(BinaryOperator::LogicAnd(hl1.expr(), hl2.expr()));
/* Replace in-edge to obb from t to pbb */ /* Replace in-edge to obb from t to pbb */
replaceInEdge(obb,thenBB,pbb); replaceInEdge(obb,thenBB,pbb);
@ -568,13 +568,13 @@ bool Function::Case_notX_and_Y(BB* pbb, BB* thenBB, BB* elseBB)
bool Function::Case_X_or_Y(BB* pbb, BB* thenBB, BB* elseBB) bool Function::Case_X_or_Y(BB* pbb, BB* thenBB, BB* elseBB)
{ {
HLTYPE &hl1(*pbb->back().hl()); HLTYPE &hl1(*pbb->back().hlU());
HLTYPE &hl2(*thenBB->back().hl()); HLTYPE &hl2(*thenBB->back().hlU());
BB * obb = thenBB->edges[THEN].BBptr; BB * obb = thenBB->edges[THEN].BBptr;
/* Construct compound DBL_OR expression */ /* Construct compound DBL_OR expression */
hl1.expr(COND_EXPR::boolOp (hl1.expr(), hl2.expr(), DBL_OR)); hl1.expr(BinaryOperator::LogicOr(hl1.expr(), hl2.expr()));
/* Replace in-edge to obb from t to pbb */ /* Replace in-edge to obb from t to pbb */

View File

@ -30,7 +30,7 @@ struct ExpStack
boolT empty(); boolT empty();
void processExpPush(int &numHlIcodes, iICODE picode) void processExpPush(int &numHlIcodes, iICODE picode)
{ {
push(picode->hl()->expr()); push(picode->hlU()->expr());
picode->invalidate(); picode->invalidate();
numHlIcodes--; numHlIcodes--;
} }
@ -96,11 +96,11 @@ static COND_EXPR *srcIdent (const LLInst &ll_insn, Function * pProc, iICODE i, I
if (ll_insn.testFlags(I)) /* immediate operand */ if (ll_insn.testFlags(I)) /* immediate operand */
{ {
if (ll_insn.testFlags(B)) if (ll_insn.testFlags(B))
return COND_EXPR::idKte (ll_insn.src().getImm2(), 1); return AstIdent::Kte (ll_insn.src().getImm2(), 1);
return COND_EXPR::idKte (ll_insn.src().getImm2(), 2); return AstIdent::Kte (ll_insn.src().getImm2(), 2);
} }
// otherwise // otherwise
return COND_EXPR::id (ll_insn, SRC, pProc, i, duIcode, du); return AstIdent::id (ll_insn, SRC, pProc, i, duIcode, du);
} }
@ -108,7 +108,7 @@ static COND_EXPR *srcIdent (const LLInst &ll_insn, Function * pProc, iICODE i, I
static COND_EXPR *dstIdent (const LLInst & ll_insn, Function * pProc, iICODE i, ICODE & duIcode, operDu du) static COND_EXPR *dstIdent (const LLInst & ll_insn, Function * pProc, iICODE i, ICODE & duIcode, operDu du)
{ {
COND_EXPR *n; COND_EXPR *n;
n = COND_EXPR::id (ll_insn, DST, pProc, i, duIcode, du); n = AstIdent::id (ll_insn, DST, pProc, i, duIcode, du);
/** Is it needed? (pIcode->ll()->flg) & NO_SRC_B **/ /** Is it needed? (pIcode->ll()->flg) & NO_SRC_B **/
return (n); return (n);
} }
@ -122,7 +122,7 @@ void Function::elimCondCodes ()
boolT notSup; /* Use/def combination not supported */ boolT notSup; /* Use/def combination not supported */
COND_EXPR *rhs; /* Source operand */ COND_EXPR *rhs; /* Source operand */
COND_EXPR *lhs; /* Destination operand */ COND_EXPR *lhs; /* Destination operand */
COND_EXPR *_expr; /* Boolean expression */ BinaryOperator *_expr; /* Boolean expression */
//BB * pBB; /* Pointer to BBs in dfs last ordering */ //BB * pBB; /* Pointer to BBs in dfs last ordering */
riICODE useAt; /* Instruction that used flag */ riICODE useAt; /* Instruction that used flag */
riICODE defAt; /* Instruction that defined flag */ riICODE defAt; /* Instruction that defined flag */
@ -133,6 +133,7 @@ void Function::elimCondCodes ()
//auto reversed_instructions = pBB->range() | reversed; //auto reversed_instructions = pBB->range() | reversed;
for (useAt = pBB->rbegin(); useAt != pBB->rend(); useAt++) for (useAt = pBB->rbegin(); useAt != pBB->rend(); useAt++)
{ {
ICODE &useIcode(*useAt);
llIcode useAtOp = llIcode(useAt->ll()->getOpcode()); llIcode useAtOp = llIcode(useAt->ll()->getOpcode());
use = useAt->ll()->flagDU.u; use = useAt->ll()->flagDU.u;
if ((useAt->type != LOW_LEVEL) || ( ! useAt->valid() ) || ( 0 == use )) if ((useAt->type != LOW_LEVEL) || ( ! useAt->valid() ) || ( 0 == use ))
@ -142,6 +143,7 @@ void Function::elimCondCodes ()
++defAt; ++defAt;
for (; defAt != pBB->rend(); defAt++) for (; defAt != pBB->rend(); defAt++)
{ {
ICODE &defIcode(*defAt);
def = defAt->ll()->flagDU.d; def = defAt->ll()->flagDU.d;
if ((use & def) != use) if ((use & def) != use)
continue; continue;
@ -160,21 +162,29 @@ void Function::elimCondCodes ()
lhs = defAt->hl()->asgn.lhs->clone(); lhs = defAt->hl()->asgn.lhs->clone();
useAt->copyDU(*defAt, eUSE, eDEF); useAt->copyDU(*defAt, eUSE, eDEF);
if (defAt->ll()->testFlags(B)) if (defAt->ll()->testFlags(B))
rhs = COND_EXPR::idKte (0, 1); rhs = AstIdent::Kte (0, 1);
else else
rhs = COND_EXPR::idKte (0, 2); rhs = AstIdent::Kte (0, 2);
break; break;
case iTEST: case iTEST:
rhs = srcIdent (*defAt->ll(),this, befDefAt,*useAt, eUSE); rhs = srcIdent (*defAt->ll(),this, befDefAt,*useAt, eUSE);
lhs = dstIdent (*defAt->ll(),this, befDefAt,*useAt, eUSE); lhs = dstIdent (*defAt->ll(),this, befDefAt,*useAt, eUSE);
lhs = COND_EXPR::boolOp (lhs, rhs, AND); lhs = BinaryOperator::And(lhs, rhs);
if (defAt->ll()->testFlags(B)) if (defAt->ll()->testFlags(B))
rhs = COND_EXPR::idKte (0, 1); rhs = AstIdent::Kte (0, 1);
else else
rhs = COND_EXPR::idKte (0, 2); rhs = AstIdent::Kte (0, 2);
break;
case iINC:
case iDEC: //WARNING: verbatim copy from iOR needs fixing ?
lhs = defAt->hl()->asgn.lhs->clone();
useAt->copyDU(*defAt, eUSE, eDEF);
if (defAt->ll()->testFlags(B))
rhs = AstIdent::Kte (0, 1);
else
rhs = AstIdent::Kte (0, 2);
break; break;
default: default:
notSup = true; notSup = true;
std::cout << hex<<defAt->loc_ip; std::cout << hex<<defAt->loc_ip;
@ -185,17 +195,17 @@ void Function::elimCondCodes ()
{ {
assert(lhs); assert(lhs);
assert(rhs); assert(rhs);
_expr = COND_EXPR::boolOp (lhs, rhs,condOpJCond[useAtOp-iJB]); _expr = BinaryOperator::Create(condOpJCond[useAtOp-iJB],lhs,rhs);
useAt->setJCond(_expr); useAt->setJCond(_expr);
} }
} }
else if (useAtOp == iJCXZ) else if (useAtOp == iJCXZ)
{ {
lhs = COND_EXPR::idReg (rCX, 0, &localId); lhs = AstIdent::Reg (rCX, 0, &localId);
useAt->setRegDU (rCX, eUSE); useAt->setRegDU (rCX, eUSE);
rhs = COND_EXPR::idKte (0, 2); rhs = AstIdent::Kte (0, 2);
_expr = COND_EXPR::boolOp (lhs, rhs, EQUAL); _expr = BinaryOperator::Create(EQUAL,lhs,rhs);
useAt->setJCond(_expr); useAt->setJCond(_expr);
} }
// else if (useAt->getOpcode() == iRCL) // else if (useAt->getOpcode() == iRCL)
@ -217,7 +227,8 @@ void Function::elimCondCodes ()
ICODE & _prev(pBB->back()); /* For extended basic blocks - previous icode inst */ ICODE & _prev(pBB->back()); /* For extended basic blocks - previous icode inst */
if (_prev.hl()->opcode == HLI_JCOND) if (_prev.hl()->opcode == HLI_JCOND)
{ {
_expr = _prev.hl()->expr()->clone(); _expr = dynamic_cast<BinaryOperator *>(_prev.hl()->expr()->clone());
assert(_expr);
_expr->changeBoolOp (condOpJCond[useAtOp-iJB]); _expr->changeBoolOp (condOpJCond[useAtOp-iJB]);
useAt->copyDU(_prev, eUSE, eUSE); useAt->copyDU(_prev, eUSE, eUSE);
useAt->setJCond(_expr); useAt->setJCond(_expr);
@ -308,7 +319,7 @@ void Function::liveRegAnalysis (LivenessSet &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)
{ {
picode->hl()->expr(COND_EXPR::idID (&retVal, &localId, (++pbb->rbegin()).base())); picode->hlU()->expr(AstIdent::idID (&retVal, &localId, (++pbb->rbegin()).base()));
picode->du.use = in_liveOut; picode->du.use = in_liveOut;
} }
} }
@ -547,12 +558,20 @@ void Function::genDU1 ()
void LOCAL_ID::forwardSubs (COND_EXPR *lhs, COND_EXPR *rhs, iICODE picode, iICODE ticode, int &numHlIcodes) const void LOCAL_ID::forwardSubs (COND_EXPR *lhs, COND_EXPR *rhs, iICODE picode, iICODE ticode, int &numHlIcodes) const
{ {
bool res; bool res;
UnaryOperator *lhs_unary;
while(lhs_unary = dynamic_cast<UnaryOperator *>(lhs))
{
if(dynamic_cast<AstIdent *>(lhs_unary))
break;
lhs = lhs_unary->unaryExp;
}
AstIdent * lhs_id=dynamic_cast<AstIdent *>(lhs_unary);
assert(lhs_id);
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, id_arr[lhs->expr.ident.idNode.regiIdx].id.regi, this); res = COND_EXPR::insertSubTreeReg (ticode->hlU()->asgn.rhs,rhs, id_arr[lhs_id->ident.idNode.regiIdx].id.regi, this);
if (res) if (res)
{ {
picode->invalidate(); picode->invalidate();
@ -561,7 +580,7 @@ void LOCAL_ID::forwardSubs (COND_EXPR *lhs, COND_EXPR *rhs, iICODE picode, iICOD
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, id_arr[lhs->expr.ident.idNode.regiIdx].id.regi, this); res = COND_EXPR::insertSubTreeReg (ticode->hlU()->asgn.lhs,rhs, id_arr[lhs_id->ident.idNode.regiIdx].id.regi, this);
if (res) if (res)
{ {
picode->invalidate(); picode->invalidate();
@ -580,7 +599,7 @@ static void forwardSubsLong (int longIdx, COND_EXPR *_exp, iICODE picode, iICODE
return; return;
/* Insert on rhs of ticode, if possible */ /* Insert on rhs of ticode, if possible */
res = COND_EXPR::insertSubTreeLongReg (_exp, &ticode->hl()->asgn.rhs, longIdx); res = COND_EXPR::insertSubTreeLongReg (_exp, ticode->hlU()->asgn.rhs, longIdx);
if (res) if (res)
{ {
picode->invalidate(); picode->invalidate();
@ -589,7 +608,7 @@ static void forwardSubsLong (int longIdx, COND_EXPR *_exp, iICODE picode, iICODE
else else
{ {
/* Try to insert it on lhs of ticode*/ /* Try to insert it on lhs of ticode*/
res = COND_EXPR::insertSubTreeLongReg (_exp, &ticode->hl()->asgn.lhs, longIdx); res = COND_EXPR::insertSubTreeLongReg (_exp, ticode->hlU()->asgn.lhs, longIdx);
if (res) if (res)
{ {
picode->invalidate(); picode->invalidate();
@ -601,56 +620,6 @@ 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 (rICODE range_to_check, iICODE lastBBinst, const LOCAL_ID & locId)
{
iICODE i;
boolT res;
uint8_t regi;
switch (m_type)
{
case IDENTIFIER:
if (expr.ident.idType == REGISTER)
{
regi= locId.id_arr[expr.ident.idNode.regiIdx].id.regi;
range_to_check.advance_begin(1);
auto all_valid_and_high_level_after_start = range_to_check | filtered(ICODE::select_valid_high_level);
for (ICODE &i : all_valid_and_high_level_after_start)
if ((i.du.def & duReg[regi]).any())
return false;
if (all_valid_and_high_level_after_start.end().base() != lastBBinst)
return true;
return false;
}
else
return true;
/* else if (rhs->expr.ident.idType == LONG_VAR)
{
missing all other identifiers ****
} */
case BOOLEAN_OP:
if(0==rhs())
return false;
res = rhs()->xClear ( range_to_check, lastBBinst, locId);
if (res == false)
return false;
if(0==lhs())
return false;
return lhs()->xClear ( range_to_check, lastBBinst, locId);
case NEGATION:
case ADDRESSOF:
case DEREFERENCE:
if(0==expr.unaryExp)
return false;
return expr.unaryExp->xClear ( range_to_check, lastBBinst, locId);
default:
fprintf(stderr,"COND_EXPR::xClear unhandled type %d\n",m_type);
} /* eos */
return false;
}
bool UnaryOperator::xClear(rICODE range_to_check, iICODE lastBBinst, const LOCAL_ID &locs) bool UnaryOperator::xClear(rICODE range_to_check, iICODE lastBBinst, const LOCAL_ID &locs)
{ {
if(0==unaryExp) if(0==unaryExp)
@ -668,6 +637,26 @@ bool BinaryOperator::xClear(rICODE range_to_check, iICODE lastBBinst, const LOCA
return false; return false;
return m_lhs->xClear (range_to_check, lastBBinst, locs); return m_lhs->xClear (range_to_check, lastBBinst, locs);
} }
bool AstIdent::xClear(rICODE range_to_check, iICODE lastBBinst, const LOCAL_ID &locId)
{
iICODE i;
uint8_t regi;
if (ident.idType == REGISTER)
{
regi= locId.id_arr[ident.idNode.regiIdx].id.regi;
range_to_check.advance_begin(1);
auto all_valid_and_high_level_after_start = range_to_check | filtered(ICODE::select_valid_high_level);
for (ICODE &i : all_valid_and_high_level_after_start)
if ((i.du.def & duReg[regi]).any())
return false;
if (all_valid_and_high_level_after_start.end().base() != lastBBinst)
return true;
return false;
}
else
return true;
}
/* 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
* argument list. */ * argument list. */
@ -709,7 +698,11 @@ static int processCArg (Function * pp, Function * pProc, ICODE * picode, size_t
/* Do not update the size of k if the expression was a segment register /* Do not update the size of k if the expression was a segment register
* in a near call */ * in a near call */
if (res == false) if (res == false)
return hlTypeSize (_exp, pProc); {
if(_exp==nullptr)
return 2;
return _exp->hlTypeSize (pProc);
}
return 0; // be default we do not know the size of the argument return 0; // be default we do not know the size of the argument
} }
@ -719,35 +712,40 @@ static int processCArg (Function * pp, Function * pProc, ICODE * picode, size_t
void LOCAL_ID::processTargetIcode(iICODE picode, int &numHlIcodes, iICODE ticode,bool isLong) const void LOCAL_ID::processTargetIcode(iICODE picode, int &numHlIcodes, iICODE ticode,bool isLong) const
{ {
boolT res; boolT res;
HLTYPE &p_hl(*picode->hl()); HLTYPE &p_hl(*picode->hlU());
HLTYPE &t_hl(*ticode->hl()); HLTYPE &t_hl(*ticode->hlU());
AstIdent *lhs_ident = dynamic_cast<AstIdent *>(p_hl.asgn.lhs);
switch (t_hl.opcode) switch (t_hl.opcode)
{ {
case HLI_ASSIGN: case HLI_ASSIGN:
if(isLong) if(isLong)
{ {
forwardSubsLong (p_hl.asgn.lhs->expr.ident.idNode.longIdx, assert(lhs_ident);
forwardSubsLong (lhs_ident->ident.idNode.longIdx,
p_hl.asgn.rhs, picode,ticode, p_hl.asgn.rhs, picode,ticode,
&numHlIcodes); &numHlIcodes);
} }
else else
this->forwardSubs (p_hl.asgn.lhs, p_hl.asgn.rhs, picode, ticode, numHlIcodes); this->forwardSubs (lhs_ident, p_hl.asgn.rhs, picode, ticode, 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)
{ {
assert(lhs_ident);
res = COND_EXPR::insertSubTreeLongReg ( res = COND_EXPR::insertSubTreeLongReg (
p_hl.asgn.rhs, p_hl.asgn.rhs,
&t_hl.exp.v, t_hl.exp.v,
p_hl.asgn.lhs->expr.ident.idNode.longIdx); lhs_ident->ident.idNode.longIdx);
} }
else else
{ {
assert(lhs_ident);
res = COND_EXPR::insertSubTreeReg ( res = COND_EXPR::insertSubTreeReg (
t_hl.exp.v, t_hl.exp.v,
p_hl.asgn.rhs, p_hl.asgn.rhs,
id_arr[p_hl.asgn.lhs->expr.ident.idNode.regiIdx].id.regi, id_arr[lhs_ident->ident.idNode.regiIdx].id.regi,
this); this);
} }
if (res) if (res)
@ -802,7 +800,7 @@ void Function::processHliCall(COND_EXPR *_exp, iICODE picode)
res = picode->newStkArg (_exp,(llIcode)picode->ll()->getOpcode(), this); res = picode->newStkArg (_exp,(llIcode)picode->ll()->getOpcode(), this);
} }
if (res == false) if (res == false)
k += hlTypeSize (_exp, this); k += _exp->hlTypeSize (this);
numArgs++; numArgs++;
} }
} }
@ -846,7 +844,7 @@ void BB::findBBExps(LOCAL_ID &locals,Function *fnc)
auto valid_and_highlevel = instructions | filtered(ICODE::TypeAndValidFilter<HIGH_LEVEL>()); auto valid_and_highlevel = instructions | filtered(ICODE::TypeAndValidFilter<HIGH_LEVEL>());
for (auto picode = valid_and_highlevel.begin(); picode != valid_and_highlevel.end(); picode++) for (auto picode = valid_and_highlevel.begin(); picode != valid_and_highlevel.end(); picode++)
{ {
HLTYPE &_icHl(*picode->hl()); HLTYPE &_icHl(*picode->hlU());
numHlIcodes++; numHlIcodes++;
if (picode->du1.numRegsDef == 1) /* uint8_t/uint16_t regs */ if (picode->du1.numRegsDef == 1) /* uint8_t/uint16_t regs */
{ {
@ -880,8 +878,12 @@ void BB::findBBExps(LOCAL_ID &locals,Function *fnc)
break; break;
case HLI_POP: case HLI_POP:
// TODO: sometimes picode->du1.idx[0].uses.front() points to next basic block ?
// pop X
// lab1:
// call F() <- somehow this is marked as user of POP ?
ticode = picode->du1.idx[0].uses.front(); ticode = picode->du1.idx[0].uses.front();
ti_hl = ticode->hl(); ti_hl = ticode->hlU();
if ((picode->du.lastDefRegi & duReg[regi]).any() && if ((picode->du.lastDefRegi & duReg[regi]).any() &&
((ti_hl->opcode != HLI_CALL) && ((ti_hl->opcode != HLI_CALL) &&
(ti_hl->opcode != HLI_RET))) (ti_hl->opcode != HLI_RET)))
@ -894,15 +896,19 @@ void BB::findBBExps(LOCAL_ID &locals,Function *fnc)
break; break;
case HLI_JCOND: case HLI_PUSH: case HLI_RET: case HLI_JCOND: case HLI_PUSH: case HLI_RET:
{
AstIdent *v = dynamic_cast<AstIdent *>(_icHl.expr());
assert(v);
res = COND_EXPR::insertSubTreeReg (ti_hl->exp.v, res = COND_EXPR::insertSubTreeReg (ti_hl->exp.v,
_exp, _exp,
locals.id_arr[_icHl.expr()->expr.ident.idNode.regiIdx].id.regi, locals.id_arr[v->ident.idNode.regiIdx].id.regi,
&locals); &locals);
if (res) if (res)
{ {
picode->invalidate(); picode->invalidate();
numHlIcodes--; numHlIcodes--;
} }
}
break; break;
/****case HLI_CALL: // register arguments /****case HLI_CALL: // register arguments
@ -918,7 +924,7 @@ void BB::findBBExps(LOCAL_ID &locals,Function *fnc)
case HLI_CALL: case HLI_CALL:
ticode = picode->du1.idx[0].uses.front(); ticode = picode->du1.idx[0].uses.front();
ti_hl = ticode->hl(); ti_hl = ticode->hlU();
_retVal = &_icHl.call.proc->retVal; _retVal = &_icHl.call.proc->retVal;
switch (ti_hl->opcode) switch (ti_hl->opcode)
{ {
@ -949,8 +955,7 @@ void BB::findBBExps(LOCAL_ID &locals,Function *fnc)
} }
else /* cannot substitute function */ else /* cannot substitute function */
{ {
//picode->loc_ip auto lhs = AstIdent::idID(_retVal,&locals,picode.base());
lhs = COND_EXPR::idID(_retVal,&locals,picode.base());
picode->setAsgn(lhs, _exp); picode->setAsgn(lhs, _exp);
} }
break; break;
@ -999,13 +1004,13 @@ void BB::findBBExps(LOCAL_ID &locals,Function *fnc)
_exp = g_exp_stk.pop(); /* pop last exp pushed */ _exp = g_exp_stk.pop(); /* pop last exp pushed */
switch (ticode->hl()->opcode) { switch (ticode->hl()->opcode) {
case HLI_ASSIGN: case HLI_ASSIGN:
forwardSubsLong (_icHl.expr()->expr.ident.idNode.longIdx, forwardSubsLong (dynamic_cast<AstIdent *>(_icHl.expr())->ident.idNode.longIdx,
_exp, picode.base(), ticode, &numHlIcodes); _exp, picode.base(), ticode, &numHlIcodes);
break; break;
case HLI_JCOND: case HLI_PUSH: case HLI_JCOND: case HLI_PUSH:
res = COND_EXPR::insertSubTreeLongReg (_exp, res = COND_EXPR::insertSubTreeLongReg (_exp,
&ticode->hl()->exp.v, ticode->hlU()->exp.v,
_icHl.asgn.lhs->expr.ident.idNode.longIdx); dynamic_cast<AstIdent *>(_icHl.asgn.lhs)->ident.idNode.longIdx);
if (res) if (res)
{ {
picode->invalidate(); picode->invalidate();
@ -1026,17 +1031,17 @@ void BB::findBBExps(LOCAL_ID &locals,Function *fnc)
{ {
case HLI_ASSIGN: case HLI_ASSIGN:
_exp = _icHl.call.toId(); _exp = _icHl.call.toId();
ticode->hl()->asgn.lhs = ticode->hlU()->asgn.lhs =
COND_EXPR::idLong(&locals, DST, AstIdent::idLong(&locals, DST,
ticode,HIGH_FIRST, picode.base(), ticode,HIGH_FIRST, picode.base(),
eDEF, *(++iICODE(ticode))->ll()); eDEF, *(++iICODE(ticode))->ll());
ticode->hl()->asgn.rhs = _exp; ticode->hlU()->asgn.rhs = _exp;
picode->invalidate(); picode->invalidate();
numHlIcodes--; numHlIcodes--;
break; break;
case HLI_PUSH: case HLI_RET: case HLI_PUSH: case HLI_RET:
ticode->hl()->expr( _icHl.call.toId() ); ticode->hlU()->expr( _icHl.call.toId() );
picode->invalidate(); picode->invalidate();
numHlIcodes--; numHlIcodes--;
break; break;
@ -1045,7 +1050,7 @@ void BB::findBBExps(LOCAL_ID &locals,Function *fnc)
_exp = _icHl.call.toId(); _exp = _icHl.call.toId();
_retVal = &picode->hl()->call.proc->retVal; _retVal = &picode->hl()->call.proc->retVal;
res = COND_EXPR::insertSubTreeLongReg (_exp, res = COND_EXPR::insertSubTreeLongReg (_exp,
&ticode->hl()->exp.v, ticode->hlU()->exp.v,
locals.newLongReg ( _retVal->type, _retVal->id.longId.h, locals.newLongReg ( _retVal->type, _retVal->id.longId.h,
_retVal->id.longId.l, picode.base())); _retVal->id.longId.l, picode.base()));
if (res) /* was substituted */ if (res) /* was substituted */
@ -1055,7 +1060,7 @@ void BB::findBBExps(LOCAL_ID &locals,Function *fnc)
} }
else /* cannot substitute function */ else /* cannot substitute function */
{ {
lhs = locals.createId(_retVal,picode.base()); auto lhs = locals.createId(_retVal,picode.base());
picode->setAsgn(lhs, _exp); picode->setAsgn(lhs, _exp);
} }
break; break;
@ -1093,8 +1098,8 @@ void BB::findBBExps(LOCAL_ID &locals,Function *fnc)
* assign it to the corresponding registers */ * assign it to the corresponding registers */
if ( not _icHl.call.proc->isLibrary() and (not picode->du1.used(0)) and (picode->du1.numRegsDef > 0)) if ( not _icHl.call.proc->isLibrary() and (not picode->du1.used(0)) and (picode->du1.numRegsDef > 0))
{ {
_exp = COND_EXPR::idFunc (_icHl.call.proc, _icHl.call.args); _exp = AstIdent::idFunc (_icHl.call.proc, _icHl.call.args);
lhs = COND_EXPR::idID (&_icHl.call.proc->retVal, &locals, picode.base()); auto lhs = AstIdent::idID (&_icHl.call.proc->retVal, &locals, picode.base());
picode->setAsgn(lhs, _exp); picode->setAsgn(lhs, _exp);
} }
} }

View File

@ -40,6 +40,7 @@ static char buf[lineSize]; /* Line buffer for hl icode output */
/* Places the new HLI_ASSIGN high-level operand in the high-level icode array */ /* Places the new HLI_ASSIGN high-level operand in the high-level icode array */
void HLTYPE::setAsgn(COND_EXPR *lhs, COND_EXPR *rhs) void HLTYPE::setAsgn(COND_EXPR *lhs, COND_EXPR *rhs)
{ {
assert(lhs);
set(lhs,rhs); set(lhs,rhs);
} }
@ -51,14 +52,12 @@ void ICODE::checkHlCall()
void ICODE::newCallHl() void ICODE::newCallHl()
{ {
type = HIGH_LEVEL; type = HIGH_LEVEL;
hl()->opcode = HLI_CALL; hlU()->setCall(ll()->src().proc.proc);
hl()->call.proc = ll()->src().proc.proc;
hl()->call.args = new STKFRAME;
if (ll()->src().proc.cb != 0) if (ll()->src().proc.cb != 0)
hl()->call.args->cb = ll()->src().proc.cb; hlU()->call.args->cb = ll()->src().proc.cb;
else if(hl()->call.proc) else if(hl()->call.proc)
hl()->call.args->cb =hl()->call.proc->cbParam; hlU()->call.args->cb = hl()->call.proc->cbParam;
else else
{ {
printf("Function with no cb set, and no valid oper.call.proc , probaby indirect call\n"); printf("Function with no cb set, and no valid oper.call.proc , probaby indirect call\n");
@ -72,7 +71,7 @@ void ICODE::newCallHl()
void ICODE::setUnary(hlIcode op, COND_EXPR *_exp) void ICODE::setUnary(hlIcode op, COND_EXPR *_exp)
{ {
type = HIGH_LEVEL; type = HIGH_LEVEL;
hl()->set(op,_exp); hlU()->set(op,_exp);
} }
@ -80,7 +79,7 @@ void ICODE::setUnary(hlIcode op, COND_EXPR *_exp)
void ICODE::setJCond(COND_EXPR *cexp) void ICODE::setJCond(COND_EXPR *cexp)
{ {
type = HIGH_LEVEL; type = HIGH_LEVEL;
hl()->set(HLI_JCOND,cexp); hlU()->set(HLI_JCOND,cexp);
} }
@ -116,7 +115,7 @@ bool ICODE::removeDefRegi (eReg regi, int thisDefIdx, LOCAL_ID *locId)
invalidate(); invalidate();
return true; return true;
} }
HlTypeSupport *p=hl()->get(); HlTypeSupport *p=hlU()->get();
if(p and p->removeRegFromLong(regi,locId)) if(p and p->removeRegFromLong(regi,locId))
{ {
du1.numRegsDef--; du1.numRegsDef--;
@ -168,7 +167,7 @@ HLTYPE LLInst::toHighLevel(COND_EXPR *lhs,COND_EXPR *rhs,Function *func)
break; break;
case iDEC: case iDEC:
rhs = COND_EXPR::idKte (1, 2); rhs = AstIdent::idKte (1, 2);
rhs = COND_EXPR::boolOp (lhs, rhs, SUB); rhs = COND_EXPR::boolOp (lhs, rhs, SUB);
res.setAsgn(lhs, rhs); res.setAsgn(lhs, rhs);
break; break;
@ -178,12 +177,12 @@ HLTYPE LLInst::toHighLevel(COND_EXPR *lhs,COND_EXPR *rhs,Function *func)
rhs = COND_EXPR::boolOp (lhs, rhs, DIV); rhs = COND_EXPR::boolOp (lhs, rhs, DIV);
if ( ll->testFlags(B) ) if ( ll->testFlags(B) )
{ {
lhs = COND_EXPR::idReg (rAL, 0, &localId); lhs = AstIdent::idReg (rAL, 0, &localId);
pIcode->setRegDU( rAL, eDEF); pIcode->setRegDU( rAL, eDEF);
} }
else else
{ {
lhs = COND_EXPR::idReg (rAX, 0, &localId); lhs = AstIdent::idReg (rAX, 0, &localId);
pIcode->setRegDU( rAX, eDEF); pIcode->setRegDU( rAX, eDEF);
} }
res.setAsgn(lhs, rhs); res.setAsgn(lhs, rhs);
@ -191,12 +190,12 @@ HLTYPE LLInst::toHighLevel(COND_EXPR *lhs,COND_EXPR *rhs,Function *func)
case iIMUL: case iIMUL:
rhs = COND_EXPR::boolOp (lhs, rhs, MUL); rhs = COND_EXPR::boolOp (lhs, rhs, MUL);
lhs = COND_EXPR::id (*pIcode, LHS_OP, func, i, *pIcode, NONE); lhs = AstIdent::id (*pIcode, LHS_OP, func, i, *pIcode, NONE);
res.setAsgn(lhs, rhs); res.setAsgn(lhs, rhs);
break; break;
case iINC: case iINC:
rhs = COND_EXPR::idKte (1, 2); rhs = AstIdent::idKte (1, 2);
rhs = COND_EXPR::boolOp (lhs, rhs, ADD); rhs = COND_EXPR::boolOp (lhs, rhs, ADD);
res.setAsgn(lhs, rhs); res.setAsgn(lhs, rhs);
break; break;
@ -210,12 +209,12 @@ HLTYPE LLInst::toHighLevel(COND_EXPR *lhs,COND_EXPR *rhs,Function *func)
rhs = COND_EXPR::boolOp (lhs, rhs, MOD); rhs = COND_EXPR::boolOp (lhs, rhs, MOD);
if ( ll->testFlags(B) ) if ( ll->testFlags(B) )
{ {
lhs = COND_EXPR::idReg (rAH, 0, &localId); lhs = AstIdent::idReg (rAH, 0, &localId);
pIcode->setRegDU( rAH, eDEF); pIcode->setRegDU( rAH, eDEF);
} }
else else
{ {
lhs = COND_EXPR::idReg (rDX, 0, &localId); lhs = AstIdent::idReg (rDX, 0, &localId);
pIcode->setRegDU( rDX, eDEF); pIcode->setRegDU( rDX, eDEF);
} }
res.setAsgn(lhs, rhs); res.setAsgn(lhs, rhs);
@ -226,7 +225,7 @@ HLTYPE LLInst::toHighLevel(COND_EXPR *lhs,COND_EXPR *rhs,Function *func)
case iMUL: case iMUL:
rhs = COND_EXPR::boolOp (lhs, rhs, MUL); rhs = COND_EXPR::boolOp (lhs, rhs, MUL);
lhs = COND_EXPR::id (*pIcode, LHS_OP, this, i, *pIcode, NONE); lhs = AstIdent::id (*pIcode, LHS_OP, this, i, *pIcode, NONE);
res.setAsgn(lhs, rhs); res.setAsgn(lhs, rhs);
break; break;
@ -294,7 +293,8 @@ void Function::highLevelGen()
{ {
size_t numIcode; /* number of icode instructions */ size_t numIcode; /* number of icode instructions */
iICODE pIcode; /* ptr to current icode node */ iICODE pIcode; /* ptr to current icode node */
COND_EXPR *lhs, *rhs; /* left- and right-hand side of expression */ COND_EXPR *lhs;
COND_EXPR *rhs; /* left- and right-hand side of expression */
uint32_t _flg; /* icode flags */ uint32_t _flg; /* icode flags */
numIcode = Icode.size(); numIcode = Icode.size();
for (iICODE i = Icode.begin(); i!=Icode.end() ; ++i) for (iICODE i = Icode.begin(); i!=Icode.end() ; ++i)
@ -311,18 +311,18 @@ void Function::highLevelGen()
if ((_flg & NO_OPS) != NO_OPS) /* if there are opers */ if ((_flg & NO_OPS) != NO_OPS) /* if there are opers */
{ {
if ( not ll->testFlags(NO_SRC) ) /* if there is src op */ if ( not ll->testFlags(NO_SRC) ) /* if there is src op */
rhs = COND_EXPR::id (*pIcode->ll(), SRC, this, i, *pIcode, NONE); rhs = AstIdent::id (*pIcode->ll(), SRC, this, i, *pIcode, NONE);
lhs = COND_EXPR::id (*pIcode->ll(), DST, this, i, *pIcode, NONE); lhs = AstIdent::id (*pIcode->ll(), DST, this, i, *pIcode, NONE);
} }
switch (ll->getOpcode()) switch (ll->getOpcode())
{ {
case iADD: case iADD:
rhs = COND_EXPR::boolOp (lhs, rhs, ADD); rhs = new BinaryOperator(ADD,lhs, rhs);
pIcode->setAsgn(lhs, rhs); pIcode->setAsgn(lhs, rhs);
break; break;
case iAND: case iAND:
rhs = COND_EXPR::boolOp (lhs, rhs, AND); rhs = BinaryOperator::And(lhs, rhs);
pIcode->setAsgn(lhs, rhs); pIcode->setAsgn(lhs, rhs);
break; break;
@ -333,54 +333,54 @@ void Function::highLevelGen()
break; break;
case iDEC: case iDEC:
rhs = COND_EXPR::idKte (1, 2); rhs = AstIdent::Kte (1, 2);
rhs = COND_EXPR::boolOp (lhs, rhs, SUB); rhs = new BinaryOperator(SUB,lhs, rhs);
pIcode->setAsgn(lhs, rhs); pIcode->setAsgn(lhs, rhs);
break; break;
case iDIV: case iDIV:
case iIDIV:/* should be signed div */ case iIDIV:/* should be signed div */
rhs = COND_EXPR::boolOp (lhs, rhs, DIV); rhs = new BinaryOperator(DIV,lhs, rhs);
if ( ll->testFlags(B) ) if ( ll->testFlags(B) )
{ {
lhs = COND_EXPR::idReg (rAL, 0, &localId); lhs = AstIdent::Reg (rAL, 0, &localId);
pIcode->setRegDU( rAL, eDEF); pIcode->setRegDU( rAL, eDEF);
} }
else else
{ {
lhs = COND_EXPR::idReg (rAX, 0, &localId); lhs = AstIdent::Reg (rAX, 0, &localId);
pIcode->setRegDU( rAX, eDEF); pIcode->setRegDU( rAX, eDEF);
} }
pIcode->setAsgn(lhs, rhs); pIcode->setAsgn(lhs, rhs);
break; break;
case iIMUL: case iIMUL:
rhs = COND_EXPR::boolOp (lhs, rhs, MUL); rhs = new BinaryOperator(MUL,lhs, rhs);
lhs = COND_EXPR::id (*ll, LHS_OP, this, i, *pIcode, NONE); lhs = AstIdent::id (*ll, LHS_OP, this, i, *pIcode, NONE);
pIcode->setAsgn(lhs, rhs); pIcode->setAsgn(lhs, rhs);
break; break;
case iINC: case iINC:
rhs = COND_EXPR::idKte (1, 2); rhs = AstIdent::Kte (1, 2);
rhs = COND_EXPR::boolOp (lhs, rhs, ADD); rhs = new BinaryOperator(ADD,lhs, rhs);
pIcode->setAsgn(lhs, rhs); pIcode->setAsgn(lhs, rhs);
break; break;
case iLEA: case iLEA:
rhs = COND_EXPR::unary (ADDRESSOF, rhs); rhs =UnaryOperator::Create(ADDRESSOF, rhs);
pIcode->setAsgn(lhs, rhs); pIcode->setAsgn(lhs, rhs);
break; break;
case iMOD: case iMOD:
rhs = COND_EXPR::boolOp (lhs, rhs, MOD); rhs = new BinaryOperator(MOD,lhs, rhs);
if ( ll->testFlags(B) ) if ( ll->testFlags(B) )
{ {
lhs = COND_EXPR::idReg (rAH, 0, &localId); lhs = AstIdent::Reg (rAH, 0, &localId);
pIcode->setRegDU( rAH, eDEF); pIcode->setRegDU( rAH, eDEF);
} }
else else
{ {
lhs = COND_EXPR::idReg (rDX, 0, &localId); lhs = AstIdent::Reg (rDX, 0, &localId);
pIcode->setRegDU( rDX, eDEF); pIcode->setRegDU( rDX, eDEF);
} }
pIcode->setAsgn(lhs, rhs); pIcode->setAsgn(lhs, rhs);
@ -390,23 +390,23 @@ void Function::highLevelGen()
break; break;
case iMUL: case iMUL:
rhs = COND_EXPR::boolOp (lhs, rhs, MUL); rhs = new BinaryOperator(MUL,lhs, rhs);
lhs = COND_EXPR::id (*ll, LHS_OP, this, i, *pIcode, NONE); lhs = AstIdent::id (*ll, LHS_OP, this, i, *pIcode, NONE);
pIcode->setAsgn(lhs, rhs); pIcode->setAsgn(lhs, rhs);
break; break;
case iNEG: case iNEG:
rhs = COND_EXPR::unary (NEGATION, lhs); rhs = UnaryOperator::Create(NEGATION, lhs);
pIcode->setAsgn(lhs, rhs); pIcode->setAsgn(lhs, rhs);
break; break;
case iNOT: case iNOT:
rhs = COND_EXPR::boolOp (NULL, rhs, NOT); rhs = new BinaryOperator(NOT,NULL, rhs); // TODO: change this to unary NOT ?
pIcode->setAsgn(lhs, rhs); pIcode->setAsgn(lhs, rhs);
break; break;
case iOR: case iOR:
rhs = COND_EXPR::boolOp (lhs, rhs, OR); rhs = new BinaryOperator(OR,lhs, rhs);
pIcode->setAsgn(lhs, rhs); pIcode->setAsgn(lhs, rhs);
break; break;
@ -421,13 +421,13 @@ void Function::highLevelGen()
break; break;
case iSHL: case iSHL:
rhs = COND_EXPR::boolOp (lhs, rhs, SHL); rhs = new BinaryOperator(SHL,lhs, rhs);
pIcode->setAsgn(lhs, rhs); pIcode->setAsgn(lhs, rhs);
break; break;
case iSAR: /* signed */ case iSAR: /* signed */
case iSHR: case iSHR:
rhs = COND_EXPR::boolOp (lhs, rhs, SHR); /* unsigned*/ rhs = new BinaryOperator(SHR,lhs, rhs); /* unsigned*/
pIcode->setAsgn(lhs, rhs); pIcode->setAsgn(lhs, rhs);
break; break;
@ -435,7 +435,7 @@ void Function::highLevelGen()
break; break;
case iSUB: case iSUB:
rhs = COND_EXPR::boolOp (lhs, rhs, SUB); rhs = new BinaryOperator(SUB,lhs, rhs);
pIcode->setAsgn(lhs, rhs); pIcode->setAsgn(lhs, rhs);
break; break;
@ -443,7 +443,7 @@ void Function::highLevelGen()
break; break;
case iXOR: case iXOR:
rhs = COND_EXPR::boolOp (lhs, rhs, XOR); rhs = new BinaryOperator(XOR,lhs, rhs);
pIcode->setAsgn(lhs, rhs); pIcode->setAsgn(lhs, rhs);
break; break;
} }
@ -452,49 +452,13 @@ void Function::highLevelGen()
} }
/* Modifies the given conditional operator to its inverse. This is used /**
* in if..then[..else] statements, to reflect the condition that takes the \fn COND_EXPR::inverse
* then part. */ Modifies the given conditional operator to its inverse. This is used
COND_EXPR *COND_EXPR::inverse () const in if..then[..else] statements, to reflect the condition that takes the
{ then part.
static condOp invCondOp[] = {GREATER, GREATER_EQUAL, NOT_EQUAL, EQUAL, */
LESS_EQUAL, LESS, DUMMY,DUMMY,DUMMY,DUMMY,
DUMMY, DUMMY, DUMMY, DUMMY, DUMMY, DUMMY,
DUMMY, DBL_OR, DBL_AND};
COND_EXPR *res=0;
if (m_type == BOOLEAN_OP)
{
switch ( op() )
{
case LESS_EQUAL: case LESS: case EQUAL:
case NOT_EQUAL: case GREATER: case GREATER_EQUAL:
res = this->clone();
res->boolExpr.op = invCondOp[op()];
return res;
case AND: case OR: case XOR: case NOT: case ADD:
case SUB: case MUL: case DIV: case SHR: case SHL: case MOD:
return COND_EXPR::unary (NEGATION, this->clone());
case DBL_AND: case DBL_OR:
// Binary::Create(invertop,lhs->inverse(),rhs->inverse());
res = this->clone();
res->boolExpr.op = invCondOp[op()];
res->boolExpr.lhs=lhs()->inverse ();
res->boolExpr.rhs=rhs()->inverse ();
return res;
default:
fprintf(stderr,"COND_EXPR::inverse unhandled op %d",op());
} /* eos */
}
else if (m_type == NEGATION) //TODO: memleak here
{
return expr.unaryExp->clone();
}
return this->clone();
/* other types are left unmodified */
}
/* Returns the string that represents the procedure call of tproc (ie. with /* Returns the string that represents the procedure call of tproc (ie. with
* actual parameters) */ * actual parameters) */
@ -505,7 +469,10 @@ std::string writeCall (Function * tproc, STKFRAME & args, Function * pproc, int
ostr<<tproc->name<<" ("; ostr<<tproc->name<<" (";
for(const STKSYM &sym : args) for(const STKSYM &sym : args)
{ {
ostr << walkCondExpr (sym.actual, pproc, numLoc); if(sym.actual)
ostr << sym.actual->walkCondExpr (pproc, numLoc);
else
ostr << "";
if((&sym)!=&(args.back())) if((&sym)!=&(args.back()))
ostr << ", "; ostr << ", ";
} }
@ -523,7 +490,7 @@ char *writeJcond (const HLTYPE &h, Function * pProc, int *numLoc)
strcat (buf, "if "); strcat (buf, "if ");
COND_EXPR *inverted=h.expr()->inverse(); COND_EXPR *inverted=h.expr()->inverse();
//inverseCondOp (&h.exp); //inverseCondOp (&h.exp);
std::string e = walkCondExpr (inverted, pProc, numLoc); std::string e = inverted->walkCondExpr (pProc, numLoc);
delete inverted; delete inverted;
strcat (buf, e.c_str()); strcat (buf, e.c_str());
strcat (buf, " {\n"); strcat (buf, " {\n");
@ -539,42 +506,53 @@ char *writeJcondInv (HLTYPE h, Function * pProc, int *numLoc)
memset (buf, ' ', sizeof(buf)); memset (buf, ' ', sizeof(buf));
buf[0] = '\0'; buf[0] = '\0';
strcat (buf, "if "); strcat (buf, "if ");
std::string e = walkCondExpr (h.expr(), pProc, numLoc); std::string e = h.expr()->walkCondExpr (pProc, numLoc);
strcat (buf, e.c_str()); strcat (buf, e.c_str());
strcat (buf, " {\n"); strcat (buf, " {\n");
return (buf); return (buf);
} }
string AssignType::writeOut(Function *pProc, int *numLoc) string AssignType::writeOut(Function *pProc, int *numLoc) const
{ {
ostringstream ostr; ostringstream ostr;
ostr << walkCondExpr (lhs, pProc, numLoc); ostr << lhs->walkCondExpr (pProc, numLoc);
ostr << " = "; ostr << " = ";
ostr << walkCondExpr (rhs, pProc, numLoc); ostr << rhs->walkCondExpr (pProc, numLoc);
ostr << ";\n"; ostr << ";\n";
return ostr.str(); return ostr.str();
} }
string CallType::writeOut(Function *pProc, int *numLoc) string CallType::writeOut(Function *pProc, int *numLoc) const
{ {
ostringstream ostr; ostringstream ostr;
ostr << writeCall (proc, *args, pProc,numLoc); ostr << writeCall (proc, *args, pProc,numLoc);
ostr << ";\n"; ostr << ";\n";
return ostr.str(); return ostr.str();
} }
string ExpType::writeOut(Function *pProc, int *numLoc) string ExpType::writeOut(Function *pProc, int *numLoc) const
{ {
return walkCondExpr (v, pProc, numLoc); if(v==nullptr)
return "";
return v->walkCondExpr (pProc, numLoc);
} }
void HLTYPE::set(COND_EXPR *l, COND_EXPR *r)
{
assert(l);
assert(r);
opcode = HLI_ASSIGN;
assert((asgn.lhs==0) and (asgn.rhs==0)); //prevent memory leaks
asgn.lhs=l;
asgn.rhs=r;
}
/* Returns a string with the contents of the current high-level icode. /* Returns a string with the contents of the current high-level icode.
* Note: this routine does not output the contens of HLI_JCOND icodes. This is * Note: this routine does not output the contens of HLI_JCOND icodes. This is
* done in a separate routine to be able to support the removal of * done in a separate routine to be able to support the removal of
* empty THEN clauses on an if..then..else. */ * empty THEN clauses on an if..then..else. */
string HLTYPE::write1HlIcode (Function * pProc, int *numLoc) string HLTYPE::write1HlIcode (Function * pProc, int *numLoc) const
{ {
string e; string e;
ostringstream ostr; ostringstream ostr;
HlTypeSupport *p = get(); const HlTypeSupport *p = get();
switch (opcode) switch (opcode)
{ {
case HLI_ASSIGN: case HLI_ASSIGN:

View File

@ -9,7 +9,6 @@ void HLTYPE::replaceExpr(COND_EXPR *e)
} }
HlTypeSupport *HLTYPE::get() HlTypeSupport *HLTYPE::get()
{ {
switch(opcode) switch(opcode)

View File

@ -95,3 +95,14 @@ void LLOperand::addProcInformation(int param_count, uint32_t call_conv)
proc.cb = param_count; proc.cb = param_count;
proc.proc->flg |= call_conv; proc.proc->flg |= call_conv;
} }
void HLTYPE::setCall(Function *proc)
{
opcode = HLI_CALL;
call.proc = proc;
call.args = new STKFRAME;
}
bool AssignType::removeRegFromLong(eReg regi, LOCAL_ID *locId)
{
lhs->performLongRemoval(regi,locId);
return true;
}

View File

@ -25,10 +25,11 @@ bool Idiom5::match(iICODE pIcode)
int Idiom5::action() int Idiom5::action()
{ {
COND_EXPR *rhs,*lhs,*expr; AstIdent *rhs,*lhs;
lhs = COND_EXPR::idLong (&m_func->localId, DST, m_icodes[0], LOW_FIRST, m_icodes[0], USE_DEF, *m_icodes[1]->ll()); COND_EXPR *expr;
rhs = COND_EXPR::idLong (&m_func->localId, SRC, m_icodes[0], LOW_FIRST, m_icodes[0], eUSE, *m_icodes[1]->ll()); lhs = AstIdent::idLong (&m_func->localId, DST, m_icodes[0], LOW_FIRST, m_icodes[0], USE_DEF, *m_icodes[1]->ll());
expr = COND_EXPR::boolOp (lhs, rhs, ADD); rhs = AstIdent::idLong (&m_func->localId, SRC, m_icodes[0], LOW_FIRST, m_icodes[0], eUSE, *m_icodes[1]->ll());
expr = new BinaryOperator(ADD,lhs, rhs);
m_icodes[0]->setAsgn(lhs, expr); m_icodes[0]->setAsgn(lhs, expr);
m_icodes[1]->invalidate(); m_icodes[1]->invalidate();
return 2; return 2;
@ -58,10 +59,12 @@ bool Idiom6::match(iICODE pIcode)
int Idiom6::action() int Idiom6::action()
{ {
COND_EXPR *rhs,*lhs,*expr;
lhs = COND_EXPR::idLong (&m_func->localId, DST, m_icodes[0], LOW_FIRST, m_icodes[0], USE_DEF, *m_icodes[1]->ll()); AstIdent *rhs,*lhs;
rhs = COND_EXPR::idLong (&m_func->localId, SRC, m_icodes[0], LOW_FIRST, m_icodes[0], eUSE, *m_icodes[1]->ll()); COND_EXPR *expr;
expr = COND_EXPR::boolOp (lhs, rhs, SUB); lhs = AstIdent::idLong (&m_func->localId, DST, m_icodes[0], LOW_FIRST, m_icodes[0], USE_DEF, *m_icodes[1]->ll());
rhs = AstIdent::idLong (&m_func->localId, SRC, m_icodes[0], LOW_FIRST, m_icodes[0], eUSE, *m_icodes[1]->ll());
expr = new BinaryOperator(SUB,lhs, rhs);
m_icodes[0]->setAsgn(lhs, expr); m_icodes[0]->setAsgn(lhs, expr);
m_icodes[1]->invalidate(); m_icodes[1]->invalidate();
return 2; return 2;
@ -165,10 +168,10 @@ int Idiom18::action() // action length
{ {
COND_EXPR *rhs,*lhs;/* Pointers to left and right hand side exps */ COND_EXPR *rhs,*lhs;/* Pointers to left and right hand side exps */
COND_EXPR *expr; COND_EXPR *expr;
lhs = COND_EXPR::id (*m_icodes[0]->ll(), SRC, m_func, m_icodes[1], *m_icodes[1], eUSE); lhs = AstIdent::id (*m_icodes[0]->ll(), SRC, m_func, m_icodes[1], *m_icodes[1], eUSE);
lhs = COND_EXPR::unary ( m_is_dec ? POST_DEC : POST_INC, lhs); lhs = UnaryOperator::Create(m_is_dec ? POST_DEC : POST_INC, lhs);
rhs = COND_EXPR::id (*m_icodes[2]->ll(), SRC, m_func, m_icodes[1], *m_icodes[3], eUSE); rhs = AstIdent::id (*m_icodes[2]->ll(), SRC, m_func, m_icodes[1], *m_icodes[3], eUSE);
expr = COND_EXPR::boolOp (lhs, rhs, condOpJCond[m_icodes[3]->ll()->getOpcode() - iJB]); expr = new BinaryOperator(condOpJCond[m_icodes[3]->ll()->getOpcode() - iJB],lhs, rhs);
m_icodes[3]->setJCond(expr); m_icodes[3]->setJCond(expr);
m_icodes[0]->invalidate(); m_icodes[0]->invalidate();
@ -220,10 +223,10 @@ int Idiom19::action()
{ {
COND_EXPR *lhs,*rhs,*expr; COND_EXPR *lhs,*rhs,*expr;
ICODE &ic1(*m_icodes[1]); ICODE &ic1(*m_icodes[1]);
lhs = COND_EXPR::id (*m_icodes[0]->ll(), DST, m_func, m_icodes[0], *m_icodes[1], eUSE); lhs = AstIdent::id (*m_icodes[0]->ll(), DST, m_func, m_icodes[0], *m_icodes[1], eUSE);
lhs = COND_EXPR::unary (m_is_dec ? PRE_DEC : PRE_INC, lhs); lhs = UnaryOperator::Create(m_is_dec ? PRE_DEC : PRE_INC, lhs);
rhs = COND_EXPR::idKte (0, 2); rhs = AstIdent::Kte (0, 2);
expr = COND_EXPR::boolOp (lhs, rhs, condOpJCond[m_icodes[1]->ll()->getOpcode() - iJB]); expr = new BinaryOperator(condOpJCond[m_icodes[1]->ll()->getOpcode() - iJB],lhs, rhs);
m_icodes[1]->setJCond(expr); m_icodes[1]->setJCond(expr);
m_icodes[0]->invalidate(); m_icodes[0]->invalidate();
return 2; return 2;
@ -310,10 +313,10 @@ bool Idiom20::match(iICODE picode)
int Idiom20::action() int Idiom20::action()
{ {
COND_EXPR *lhs,*rhs,*expr; COND_EXPR *lhs,*rhs,*expr;
lhs = COND_EXPR::id (*m_icodes[1]->ll(), SRC, m_func, m_icodes[0], *m_icodes[0], eUSE); lhs = AstIdent::id (*m_icodes[1]->ll(), SRC, m_func, m_icodes[0], *m_icodes[0], eUSE);
lhs = COND_EXPR::unary (m_is_dec, lhs); lhs = UnaryOperator::Create(m_is_dec, lhs);
rhs = COND_EXPR::id (*m_icodes[2]->ll(), SRC, m_func, m_icodes[0], *m_icodes[3], eUSE); rhs = AstIdent::id (*m_icodes[2]->ll(), SRC, m_func, m_icodes[0], *m_icodes[3], eUSE);
expr = COND_EXPR::boolOp (lhs, rhs, condOpJCond[m_icodes[3]->ll()->getOpcode() - iJB]); expr = new BinaryOperator(condOpJCond[m_icodes[3]->ll()->getOpcode() - iJB],lhs, rhs);
m_icodes[3]->setJCond(expr); m_icodes[3]->setJCond(expr);
for(int i=0; i<3; ++i) for(int i=0; i<3; ++i)
m_icodes[i]->invalidate(); m_icodes[i]->invalidate();

View File

@ -49,11 +49,13 @@ bool Idiom14::match(iICODE pIcode)
int Idiom14::action() int Idiom14::action()
{ {
int idx; int idx;
COND_EXPR *lhs,*rhs; AstIdent *lhs;
COND_EXPR *rhs;
idx = m_func->localId.newLongReg (TYPE_LONG_SIGN, m_regH, m_regL, m_icodes[0]); idx = m_func->localId.newLongReg (TYPE_LONG_SIGN, m_regH, m_regL, m_icodes[0]);
lhs = COND_EXPR::idLongIdx (idx); lhs = AstIdent::LongIdx (idx);
m_icodes[0]->setRegDU( m_regH, eDEF); m_icodes[0]->setRegDU( m_regH, eDEF);
rhs = COND_EXPR::id (*m_icodes[0]->ll(), SRC, m_func, m_icodes[0], *m_icodes[0], NONE); rhs = AstIdent::id (*m_icodes[0]->ll(), SRC, m_func, m_icodes[0], *m_icodes[0], NONE);
m_icodes[0]->setAsgn(lhs, rhs); m_icodes[0]->setAsgn(lhs, rhs);
m_icodes[1]->invalidate(); m_icodes[1]->invalidate();
return 2; return 2;
@ -98,11 +100,12 @@ bool Idiom13::match(iICODE pIcode)
int Idiom13::action() int Idiom13::action()
{ {
COND_EXPR *lhs,*rhs; AstIdent *lhs;
lhs = COND_EXPR::idReg (m_loaded_reg, 0, &m_func->localId); COND_EXPR *rhs;
lhs = AstIdent::Reg (m_loaded_reg, 0, &m_func->localId);
m_icodes[0]->setRegDU( m_loaded_reg, eDEF); m_icodes[0]->setRegDU( m_loaded_reg, eDEF);
m_icodes[0]->du1.numRegsDef--; /* prev uint8_t reg def */ m_icodes[0]->du1.numRegsDef--; /* prev uint8_t reg def */
rhs = COND_EXPR::id (*m_icodes[0]->ll(), SRC, m_func, m_icodes[0], *m_icodes[0], NONE); rhs = AstIdent::id (*m_icodes[0]->ll(), SRC, m_func, m_icodes[0], *m_icodes[0], NONE);
m_icodes[0]->setAsgn(lhs, rhs); m_icodes[0]->setAsgn(lhs, rhs);
m_icodes[1]->invalidate(); m_icodes[1]->invalidate();
return 2; return 2;

View File

@ -52,9 +52,10 @@ bool Idiom11::match (iICODE picode)
} }
int Idiom11::action() int Idiom11::action()
{ {
COND_EXPR *lhs,*rhs; AstIdent *lhs;
lhs = COND_EXPR::idLong (&m_func->localId, DST, m_icodes[0], HIGH_FIRST,m_icodes[0], USE_DEF, *m_icodes[1]->ll()); COND_EXPR *rhs;
rhs = COND_EXPR::unary (NEGATION, lhs); lhs = AstIdent::idLong (&m_func->localId, DST, m_icodes[0], HIGH_FIRST,m_icodes[0], USE_DEF, *m_icodes[1]->ll());
rhs = UnaryOperator::Create(NEGATION, lhs);
m_icodes[0]->setAsgn(lhs, rhs); m_icodes[0]->setAsgn(lhs, rhs);
m_icodes[1]->invalidate(); m_icodes[1]->invalidate();
m_icodes[2]->invalidate(); m_icodes[2]->invalidate();
@ -94,9 +95,10 @@ bool Idiom16::match (iICODE picode)
} }
int Idiom16::action() int Idiom16::action()
{ {
COND_EXPR *lhs,*rhs; AstIdent *lhs;
lhs = COND_EXPR::idReg (m_icodes[0]->ll()->dst.regi, m_icodes[0]->ll()->getFlag(),&m_func->localId); COND_EXPR *rhs;
rhs = COND_EXPR::unary (NEGATION, lhs->clone()); lhs = AstIdent::Reg (m_icodes[0]->ll()->dst.regi, m_icodes[0]->ll()->getFlag(),&m_func->localId);
rhs = UnaryOperator::Create(NEGATION, lhs->clone());
m_icodes[0]->setAsgn(lhs, rhs); m_icodes[0]->setAsgn(lhs, rhs);
m_icodes[1]->invalidate(); m_icodes[1]->invalidate();
m_icodes[2]->invalidate(); m_icodes[2]->invalidate();

View File

@ -28,16 +28,17 @@ bool Idiom8::match(iICODE pIcode)
int Idiom8::action() int Idiom8::action()
{ {
int idx; int idx;
COND_EXPR *rhs,*lhs,*expr; AstIdent *lhs;
COND_EXPR *rhs,*expr;
eReg regH,regL; eReg regH,regL;
regH=m_icodes[0]->ll()->dst.regi; regH=m_icodes[0]->ll()->dst.regi;
regL=m_icodes[1]->ll()->dst.regi; regL=m_icodes[1]->ll()->dst.regi;
idx = m_func->localId.newLongReg (TYPE_LONG_SIGN, regH, regL, m_icodes[0]); idx = m_func->localId.newLongReg (TYPE_LONG_SIGN, regH, regL, m_icodes[0]);
lhs = COND_EXPR::idLongIdx (idx); lhs = AstIdent::LongIdx (idx);
m_icodes[0]->setRegDU( regL, USE_DEF); m_icodes[0]->setRegDU( regL, USE_DEF);
rhs = COND_EXPR::idKte(1,2); rhs = AstIdent::Kte(1,2);
expr = COND_EXPR::boolOp(lhs, rhs, SHR); expr = new BinaryOperator(SHR,lhs, rhs);
m_icodes[0]->setAsgn(lhs, expr); m_icodes[0]->setAsgn(lhs, expr);
m_icodes[1]->invalidate(); m_icodes[1]->invalidate();
return 2; return 2;
@ -78,12 +79,14 @@ bool Idiom15::match(iICODE pIcode)
int Idiom15::action() int Idiom15::action()
{ {
COND_EXPR *lhs,*rhs,*_exp; AstIdent *lhs;
lhs = COND_EXPR::idReg (m_icodes[0]->ll()->dst.regi,
COND_EXPR *rhs,*_exp;
lhs = AstIdent::Reg (m_icodes[0]->ll()->dst.regi,
m_icodes[0]->ll()->getFlag() & NO_SRC_B, m_icodes[0]->ll()->getFlag() & NO_SRC_B,
&m_func->localId); &m_func->localId);
rhs = COND_EXPR::idKte (m_icodes.size(), 2); rhs = AstIdent::Kte (m_icodes.size(), 2);
_exp = COND_EXPR::boolOp (lhs, rhs, SHL); _exp = new BinaryOperator(SHL,lhs, rhs);
m_icodes[0]->setAsgn(lhs, _exp); m_icodes[0]->setAsgn(lhs, _exp);
for (size_t i=1; i<m_icodes.size()-1; ++i) for (size_t i=1; i<m_icodes.size()-1; ++i)
{ {
@ -116,16 +119,18 @@ bool Idiom12::match(iICODE pIcode)
int Idiom12::action() int Idiom12::action()
{ {
int idx; int idx;
COND_EXPR *rhs,*lhs,*expr; COND_EXPR *rhs,*expr;
AstIdent *lhs;
eReg regH,regL; eReg regH,regL;
regL=m_icodes[0]->ll()->dst.regi; regL=m_icodes[0]->ll()->dst.regi;
regH=m_icodes[1]->ll()->dst.regi; regH=m_icodes[1]->ll()->dst.regi;
idx = m_func->localId.newLongReg (TYPE_LONG_UNSIGN, regH, regL,m_icodes[0]); idx = m_func->localId.newLongReg (TYPE_LONG_UNSIGN, regH, regL,m_icodes[0]);
lhs = COND_EXPR::idLongIdx (idx); lhs = AstIdent::LongIdx (idx);
m_icodes[0]->setRegDU( regH, USE_DEF); m_icodes[0]->setRegDU( regH, USE_DEF);
rhs = COND_EXPR::idKte (1, 2); rhs = AstIdent::Kte (1, 2);
expr = COND_EXPR::boolOp (lhs, rhs, SHL); expr = new BinaryOperator(SHL,lhs, rhs);
m_icodes[0]->setAsgn(lhs, expr); m_icodes[0]->setAsgn(lhs, expr);
m_icodes[1]->invalidate(); m_icodes[1]->invalidate();
return 2; return 2;
@ -155,15 +160,16 @@ bool Idiom9::match(iICODE pIcode)
int Idiom9::action() int Idiom9::action()
{ {
int idx; int idx;
COND_EXPR *rhs,*lhs,*expr; AstIdent *lhs;
COND_EXPR *rhs,*expr;
eReg regH,regL; eReg regH,regL;
regL=m_icodes[1]->ll()->dst.regi; regL=m_icodes[1]->ll()->dst.regi;
regH=m_icodes[0]->ll()->dst.regi; regH=m_icodes[0]->ll()->dst.regi;
idx = m_func->localId.newLongReg (TYPE_LONG_UNSIGN,regH,regL,m_icodes[0]); idx = m_func->localId.newLongReg (TYPE_LONG_UNSIGN,regH,regL,m_icodes[0]);
lhs = COND_EXPR::idLongIdx (idx); lhs = AstIdent::LongIdx (idx);
m_icodes[0]->setRegDU(regL, USE_DEF); m_icodes[0]->setRegDU(regL, USE_DEF);
rhs = COND_EXPR::idKte (1, 2); rhs = AstIdent::Kte (1, 2);
expr = COND_EXPR::boolOp (lhs, rhs, SHR); expr = new BinaryOperator(SHR,lhs, rhs);
m_icodes[0]->setAsgn(lhs, expr); m_icodes[0]->setAsgn(lhs, expr);
m_icodes[1]->invalidate(); m_icodes[1]->invalidate();
return 2; return 2;

View File

@ -39,9 +39,11 @@ bool Idiom21::match (iICODE picode)
} }
int Idiom21::action() int Idiom21::action()
{ {
COND_EXPR *lhs,*rhs; COND_EXPR *rhs;
lhs = COND_EXPR::idLong (&m_func->localId, DST, m_icodes[0],HIGH_FIRST, m_icodes[0], eDEF, *m_icodes[1]->ll()); AstIdent *lhs;
rhs = COND_EXPR::idKte (m_icodes[1]->ll()->src().getImm2() , 4);
lhs = AstIdent::idLong (&m_func->localId, DST, m_icodes[0],HIGH_FIRST, m_icodes[0], eDEF, *m_icodes[1]->ll());
rhs = AstIdent::Kte (m_icodes[1]->ll()->src().getImm2() , 4);
m_icodes[0]->setAsgn(lhs, rhs); m_icodes[0]->setAsgn(lhs, rhs);
m_icodes[0]->du.use = 0; /* clear register used in iXOR */ m_icodes[0]->du.use = 0; /* clear register used in iXOR */
m_icodes[1]->invalidate(); m_icodes[1]->invalidate();
@ -82,10 +84,11 @@ bool Idiom7::match(iICODE picode)
} }
int Idiom7::action() int Idiom7::action()
{ {
COND_EXPR *lhs,*rhs; COND_EXPR *lhs;
lhs = COND_EXPR::id (*m_icode->ll(), DST, m_func, m_icode, *m_icode, NONE); COND_EXPR *rhs;
rhs = COND_EXPR::idKte (0, 2); lhs = AstIdent::id (*m_icode->ll(), DST, m_func, m_icode, *m_icode, NONE);
m_icode->setAsgn(lhs, rhs); rhs = AstIdent::Kte (0, 2);
m_icode->setAsgn(dynamic_cast<AstIdent *>(lhs), rhs);
m_icode->du.use = 0; /* clear register used in iXOR */ m_icode->du.use = 0; /* clear register used in iXOR */
m_icode->ll()->setFlags(I); m_icode->ll()->setFlags(I);
return 1; return 1;

View File

@ -176,9 +176,9 @@ int LOCAL_ID::newLongReg(hlType t, eReg regH, eReg regL, iICODE ix_)
} }
/* Returns an identifier conditional expression node of type TYPE_LONG or /* Returns an identifier conditional expression node of type TYPE_LONG or
* TYPE_WORD_SIGN */ * TYPE_WORD_SIGN */
COND_EXPR * LOCAL_ID::createId(const ID *retVal, iICODE ix_) AstIdent * LOCAL_ID::createId(const ID *retVal, iICODE ix_)
{ {
return COND_EXPR::idID(retVal,this,ix_); return AstIdent::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
@ -337,18 +337,18 @@ boolT checkLongEq (LONG_STKID_TYPE longId, iICODE pIcode, int i, Function * pPro
if ((longId.offH == pmHdst->off) && (longId.offL == pmLdst->off)) if ((longId.offH == pmHdst->off) && (longId.offL == pmLdst->off))
{ {
asgn.lhs = COND_EXPR::idLongIdx (i); asgn.lhs = AstIdent::LongIdx (i);
if ( not pIcode->ll()->testFlags(NO_SRC) ) if ( not pIcode->ll()->testFlags(NO_SRC) )
{ {
asgn.rhs = COND_EXPR::idLong (&pProc->localId, SRC, pIcode, HIGH_FIRST, pIcode, eUSE, atOffset); asgn.rhs = AstIdent::idLong (&pProc->localId, SRC, pIcode, HIGH_FIRST, pIcode, eUSE, atOffset);
} }
return true; return true;
} }
else if ((longId.offH == pmHsrc->off) && (longId.offL == pmLsrc->off)) else if ((longId.offH == pmHsrc->off) && (longId.offL == pmLsrc->off))
{ {
asgn.lhs = COND_EXPR::idLong (&pProc->localId, DST, pIcode, HIGH_FIRST, pIcode,eDEF, atOffset); asgn.lhs = AstIdent::idLong (&pProc->localId, DST, pIcode, HIGH_FIRST, pIcode,eDEF, atOffset);
asgn.rhs = COND_EXPR::idLongIdx (i); asgn.rhs = AstIdent::LongIdx (i);
return true; return true;
} }
return false; return false;
@ -377,17 +377,17 @@ boolT checkLongRegEq (LONGID_TYPE longId, iICODE pIcode, int i,
if ((longId.h == pmHdst->regi) && (longId.l == pmLdst->regi)) if ((longId.h == pmHdst->regi) && (longId.l == pmLdst->regi))
{ {
asgn.lhs = COND_EXPR::idLongIdx (i); asgn.lhs = AstIdent::LongIdx (i);
if ( not pIcode->ll()->testFlags(NO_SRC) ) if ( not pIcode->ll()->testFlags(NO_SRC) )
{ {
asgn.rhs = COND_EXPR::idLong (&pProc->localId, SRC, pIcode, HIGH_FIRST, pIcode, eUSE, atOffset); asgn.rhs = AstIdent::idLong (&pProc->localId, SRC, pIcode, HIGH_FIRST, pIcode, eUSE, atOffset);
} }
return true; return true;
} }
else if ((longId.h == pmHsrc->regi) && (longId.l == pmLsrc->regi)) else if ((longId.h == pmHsrc->regi) && (longId.l == pmLsrc->regi))
{ {
asgn.lhs = COND_EXPR::idLong (&pProc->localId, DST, pIcode, HIGH_FIRST, pIcode, eDEF, atOffset); asgn.lhs = AstIdent::idLong (&pProc->localId, DST, pIcode, HIGH_FIRST, pIcode, eDEF, atOffset);
asgn.rhs = COND_EXPR::idLongIdx (i); asgn.rhs = AstIdent::LongIdx (i);
return true; return true;
} }
return false; return false;

View File

@ -229,7 +229,8 @@ void Function::FollowCtrl(CALL_GRAPH * pcallGraph, STATE *pstate)
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:
{ STATE StCopy; {
STATE StCopy;
int ip = Icode.size()-1; /* Index of this jump */ int ip = Icode.size()-1; /* Index of this jump */
ICODE &prev(*(++Icode.rbegin())); /* Previous icode */ ICODE &prev(*(++Icode.rbegin())); /* Previous icode */
boolT fBranch = false; boolT fBranch = false;
@ -1184,9 +1185,9 @@ void Function::process_operands(ICODE & pIcode, STATE * pstate)
pIcode.du1.numRegsDef++; pIcode.du1.numRegsDef++;
case iLODS: case iLODS:
pIcode.du.addDefinedAndUsed(rSI); pIcode.du.addDefinedAndUsed(rSI);
pIcode.du.def |= duReg[(cb==2)? rAX: rAL]; pIcode.du.def.addReg((cb==2)? rAX: rAL);
pIcode.du1.numRegsDef += 2; pIcode.du1.numRegsDef += 2;
pIcode.du.use |= duReg[sseg]; pIcode.du.use.addReg(sseg);
break; break;
case iREP_OUTS: case iREP_OUTS:

View File

@ -90,7 +90,7 @@ void CALL_GRAPH::write()
* Note: register(s) are only included once in the table. */ * Note: register(s) are only included once in the table. */
void LOCAL_ID::newRegArg(iICODE picode, iICODE ticode) const void LOCAL_ID::newRegArg(iICODE picode, iICODE ticode) const
{ {
COND_EXPR *lhs; AstIdent *lhs;
STKFRAME * call_args_stackframe, *target_stackframe; STKFRAME * call_args_stackframe, *target_stackframe;
const ID *id; const ID *id;
int tidx; int tidx;
@ -106,11 +106,12 @@ void LOCAL_ID::newRegArg(iICODE picode, iICODE ticode) const
/* Get registers and index into target procedure's local list */ /* Get registers and index into target procedure's local list */
call_args_stackframe = ticode->hl()->call.args; call_args_stackframe = ticode->hl()->call.args;
target_stackframe = &tproc->args; target_stackframe = &tproc->args;
lhs = picode->hl()->asgn.lhs; lhs = dynamic_cast<AstIdent *>(picode->hl()->asgn.lhs);
type = lhs->expr.ident.idType; assert(lhs);
type = lhs->ident.idType;
if (type == REGISTER) if (type == REGISTER)
{ {
regL = id_arr[lhs->expr.ident.idNode.regiIdx].id.regi; regL = id_arr[lhs->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
@ -118,7 +119,7 @@ void LOCAL_ID::newRegArg(iICODE picode, iICODE ticode) const
} }
else if (type == LONG_VAR) else if (type == LONG_VAR)
{ {
int longIdx = lhs->expr.ident.idNode.longIdx; int longIdx = lhs->ident.idNode.longIdx;
regL = id_arr[longIdx].id.longId.l; regL = id_arr[longIdx].id.longId.l;
regH = id_arr[longIdx].id.longId.h; 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*/);
@ -132,14 +133,14 @@ void LOCAL_ID::newRegArg(iICODE picode, iICODE ticode) const
continue; continue;
if (type == REGISTER) if (type == REGISTER)
{ {
if ( tgt_sym.regs->expr.ident.idNode.regiIdx == tidx ) if ( tgt_sym.regs->ident.idNode.regiIdx == tidx )
{ {
regExist = true; regExist = true;
} }
} }
else if (type == LONG_VAR) else if (type == LONG_VAR)
{ {
if ( tgt_sym.regs->expr.ident.idNode.longIdx == tidx ) if ( tgt_sym.regs->ident.idNode.longIdx == tidx )
{ {
regExist = true; regExist = true;
} }
@ -160,18 +161,18 @@ void LOCAL_ID::newRegArg(iICODE picode, iICODE ticode) const
if (regL < rAL) if (regL < rAL)
{ {
newsym.type = TYPE_WORD_SIGN; newsym.type = TYPE_WORD_SIGN;
newsym.regs = COND_EXPR::idRegIdx(tidx, WORD_REG); newsym.regs = AstIdent::RegIdx(tidx, WORD_REG);
} }
else else
{ {
newsym.type = TYPE_BYTE_SIGN; newsym.type = TYPE_BYTE_SIGN;
newsym.regs = COND_EXPR::idRegIdx(tidx, BYTE_REG); newsym.regs = AstIdent::RegIdx(tidx, BYTE_REG);
} }
tproc->localId.id_arr[tidx].name = newsym.name; tproc->localId.id_arr[tidx].name = newsym.name;
} }
else if (type == LONG_VAR) else if (type == LONG_VAR)
{ {
newsym.regs = COND_EXPR::idLongIdx (tidx); newsym.regs = AstIdent::LongIdx (tidx);
newsym.type = TYPE_LONG_SIGN; newsym.type = TYPE_LONG_SIGN;
tproc->localId.id_arr[tidx].name = newsym.name; tproc->localId.id_arr[tidx].name = newsym.name;
tproc->localId.propLongId (regL, regH, tproc->localId.id_arr[tidx].name.c_str()); tproc->localId.propLongId (regL, regH, tproc->localId.id_arr[tidx].name.c_str());
@ -188,7 +189,7 @@ void LOCAL_ID::newRegArg(iICODE picode, iICODE ticode) const
/* 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 = &id_arr[lhs->expr.ident.idNode.regiIdx]; id = &id_arr[lhs->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;
@ -196,7 +197,7 @@ void LOCAL_ID::newRegArg(iICODE picode, iICODE ticode) const
newsym.type = TYPE_BYTE_SIGN; newsym.type = TYPE_BYTE_SIGN;
break; break;
case LONG_VAR: case LONG_VAR:
id = &id_arr[lhs->expr.ident.idNode.longIdx]; id = &id_arr[lhs->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;
@ -216,15 +217,17 @@ void LOCAL_ID::newRegArg(iICODE picode, iICODE ticode) const
*/ */
bool CallType::newStkArg(COND_EXPR *exp, llIcode opcode, Function * pproc) bool CallType::newStkArg(COND_EXPR *exp, llIcode opcode, Function * pproc)
{ {
AstIdent *expr = dynamic_cast<AstIdent *>(exp);
uint8_t regi; uint8_t regi;
/* Check for far procedure call, in which case, references to segment /* Check for far procedure call, in which case, references to segment
* registers are not be considered another parameter (i.e. they are * registers are not be considered another parameter (i.e. they are
* long references to another segment) */ * long references to another segment) */
if (exp) if (expr)
{ {
if ((exp->m_type == IDENTIFIER) && (exp->expr.ident.idType == REGISTER)) if (expr->ident.idType == REGISTER)
{ {
regi = pproc->localId.id_arr[exp->expr.ident.idNode.regiIdx].id.regi; regi = pproc->localId.id_arr[expr->ident.idNode.regiIdx].id.regi;
if ((regi >= rES) && (regi <= rDS)) if ((regi >= rES) && (regi <= rDS))
{ {
if (opcode == iCALLF) if (opcode == iCALLF)
@ -254,24 +257,25 @@ void CallType::placeStkArg (COND_EXPR *exp, int pos)
COND_EXPR *CallType::toId() COND_EXPR *CallType::toId()
{ {
return COND_EXPR::idFunc( proc, args); return AstIdent::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,
* the actual argument gets modified */ * the actual argument gets modified */
void adjustActArgType (COND_EXPR *exp, hlType forType, Function * pproc) void adjustActArgType (COND_EXPR *_exp, hlType forType, Function * pproc)
{ {
AstIdent *expr = dynamic_cast<AstIdent *>(_exp);
PROG &prog(Project::get()->prog); PROG &prog(Project::get()->prog);
hlType actType; hlType actType;
int offset, offL; int offset, offL;
if (exp == NULL) if (expr == NULL)
return; return;
actType = exp-> expType (pproc); actType = expr-> expType (pproc);
if (((actType == forType) || (exp->m_type != IDENTIFIER))) if (actType == forType)
return; return;
switch (forType) switch (forType)
{ {
@ -290,13 +294,13 @@ void adjustActArgType (COND_EXPR *exp, hlType forType, Function * pproc)
case TYPE_CONST: case TYPE_CONST:
/* It's an offset into image where a string is /* It's an offset into image where a string is
* found. Point to the string. */ * found. Point to the string. */
offL = exp->expr.ident.idNode.kte.kte; offL = expr->ident.idNode.kte.kte;
if (prog.fCOM) if (prog.fCOM)
offset = (pproc->state.r[rDS]<<4) + offL + 0x100; offset = (pproc->state.r[rDS]<<4) + offL + 0x100;
else else
offset = (pproc->state.r[rDS]<<4) + offL; offset = (pproc->state.r[rDS]<<4) + offL;
exp->expr.ident.idNode.strIdx = offset; expr->ident.idNode.strIdx = offset;
exp->expr.ident.idType = STRING; expr->ident.idType = STRING;
break; break;
case TYPE_PTR: case TYPE_PTR:

View File

@ -142,7 +142,8 @@ static int longJCond23 (Assignment &asgn, iICODE pIcode, int arc, iICODE atOffse
iICODE atOffset1(atOffset),next1(++iICODE(pIcode)); iICODE atOffset1(atOffset),next1(++iICODE(pIcode));
advance(atOffset1,1); advance(atOffset1,1);
/* Create new HLI_JCOND and condition */ /* Create new HLI_JCOND and condition */
asgn.lhs = COND_EXPR::boolOp (asgn.lhs, asgn.rhs, condOpJCond[atOffset1->ll()->getOpcode()-iJB]); condOp oper=condOpJCond[atOffset1->ll()->getOpcode()-iJB];
asgn.lhs = new BinaryOperator(oper,asgn.lhs, asgn.rhs);
next1->setJCond(asgn.lhs); next1->setJCond(asgn.lhs);
next1->copyDU(*pIcode, eUSE, eUSE); next1->copyDU(*pIcode, eUSE, eUSE);
next1->du.use |= atOffset->du.use; next1->du.use |= atOffset->du.use;
@ -177,7 +178,8 @@ static int longJCond22 (Assignment &asgn, iICODE pIcode,iICODE pEnd)
iICODE icodes[] = { pIcode++,pIcode++,pIcode++,pIcode++ }; iICODE icodes[] = { pIcode++,pIcode++,pIcode++,pIcode++ };
/* Form conditional expression */ /* Form conditional expression */
asgn.lhs = COND_EXPR::boolOp (asgn.lhs, asgn.rhs, condOpJCond[icodes[3]->ll()->getOpcode() - iJB]); condOp oper=condOpJCond[icodes[3]->ll()->getOpcode() - iJB];
asgn.lhs = new BinaryOperator(oper,asgn.lhs, asgn.rhs);
icodes[1]->setJCond(asgn.lhs); icodes[1]->setJCond(asgn.lhs);
icodes[1]->copyDU (*icodes[0], eUSE, eUSE); icodes[1]->copyDU (*icodes[0], eUSE, eUSE);
icodes[1]->du.use |= icodes[2]->du.use; icodes[1]->du.use |= icodes[2]->du.use;
@ -253,20 +255,27 @@ void Function::propLongStk (int i, const ID &pLocId)
switch (pIcode->ll()->getOpcode()) switch (pIcode->ll()->getOpcode())
{ {
case iMOV: case iMOV:
pIcode->setAsgn(asgn.lhs, asgn.rhs); pIcode->setAsgn(dynamic_cast<AstIdent *>(asgn.lhs), asgn.rhs);
next1->invalidate(); next1->invalidate();
break; break;
case iAND: case iOR: case iXOR: case iAND: case iOR: case iXOR:
{
condOp oper = DUMMY;
switch (pIcode->ll()->getOpcode()) switch (pIcode->ll()->getOpcode())
{ {
case iAND: asgn.rhs = COND_EXPR::boolOp (asgn.lhs, asgn.rhs, AND); break; case iAND: oper=AND; break;
case iOR: asgn.rhs = COND_EXPR::boolOp (asgn.lhs, asgn.rhs, OR); break; case iOR: oper=OR; break;
case iXOR: asgn.rhs = COND_EXPR::boolOp (asgn.lhs, asgn.rhs, XOR); break; case iXOR: oper=XOR; break;
} }
pIcode->setAsgn(asgn.lhs, asgn.rhs); if(DUMMY!=oper)
{
asgn.rhs = new BinaryOperator(oper,asgn.lhs, asgn.rhs);
}
pIcode->setAsgn(dynamic_cast<AstIdent *>(asgn.lhs), asgn.rhs);
next1->invalidate(); next1->invalidate();
break; break;
}
case iPUSH: case iPUSH:
pIcode->setUnary( HLI_PUSH, asgn.lhs); pIcode->setUnary( HLI_PUSH, asgn.lhs);
@ -326,8 +335,8 @@ int Function::findBackwarLongDefs(int loc_ident_idx, const ID &pLocId, iICODE be
{ {
localId.id_arr[loc_ident_idx].idx.push_back(pIcode);//idx-1//insert localId.id_arr[loc_ident_idx].idx.push_back(pIcode);//idx-1//insert
icode.setRegDU( pmL->regi, eDEF); icode.setRegDU( pmL->regi, eDEF);
asgn.lhs = COND_EXPR::idLongIdx (loc_ident_idx); asgn.lhs = AstIdent::LongIdx (loc_ident_idx);
asgn.rhs = COND_EXPR::idLong (&this->localId, SRC, pIcode, HIGH_FIRST, pIcode, eUSE, *next1->ll()); asgn.rhs = AstIdent::idLong (&this->localId, SRC, pIcode, HIGH_FIRST, pIcode, eUSE, *next1->ll());
icode.setAsgn(asgn.lhs, asgn.rhs); icode.setAsgn(asgn.lhs, asgn.rhs);
next1->invalidate(); next1->invalidate();
forced_finish=true; /* to exit the loop */ forced_finish=true; /* to exit the loop */
@ -339,7 +348,7 @@ int Function::findBackwarLongDefs(int loc_ident_idx, const ID &pLocId, iICODE be
pmL = &icode.ll()->dst; pmL = &icode.ll()->dst;
if ((pLocId.id.longId.h == pmH->regi) && (pLocId.id.longId.l == pmL->regi)) if ((pLocId.id.longId.h == pmH->regi) && (pLocId.id.longId.l == pmL->regi))
{ {
asgn.lhs = COND_EXPR::idLongIdx (loc_ident_idx); asgn.lhs = AstIdent::LongIdx (loc_ident_idx);
icode.setRegDU( pmH->regi, eDEF); icode.setRegDU( pmH->regi, eDEF);
icode.setUnary(HLI_POP, asgn.lhs); icode.setUnary(HLI_POP, asgn.lhs);
next1->invalidate(); next1->invalidate();
@ -355,19 +364,18 @@ int Function::findBackwarLongDefs(int loc_ident_idx, const ID &pLocId, iICODE be
pmH = &next1->ll()->dst; pmH = &next1->ll()->dst;
if ((pLocId.id.longId.h == pmH->regi) && (pLocId.id.longId.l == pmL->regi)) if ((pLocId.id.longId.h == pmH->regi) && (pLocId.id.longId.l == pmL->regi))
{ {
asgn.lhs = COND_EXPR::idLongIdx (loc_ident_idx); asgn.lhs = AstIdent::LongIdx (loc_ident_idx);
asgn.rhs = COND_EXPR::idLong (&this->localId, SRC, pIcode, LOW_FIRST, pIcode, eUSE, *next1->ll()); asgn.rhs = AstIdent::idLong (&this->localId, SRC, pIcode, LOW_FIRST, pIcode, eUSE, *next1->ll());
icode.setRegDU( pmH->regi, USE_DEF); icode.setRegDU( pmH->regi, USE_DEF);
condOp toCreate=DUMMY;
switch (icode.ll()->getOpcode()) switch (icode.ll()->getOpcode())
{ {
case iAND: asgn.rhs = COND_EXPR::boolOp (asgn.lhs, asgn.rhs, AND); case iAND: toCreate = AND; break;
break; case iOR: toCreate = OR; break;
case iOR: case iXOR: toCreate = XOR; break;
asgn.rhs = COND_EXPR::boolOp (asgn.lhs, asgn.rhs, OR);
break;
case iXOR: asgn.rhs = COND_EXPR::boolOp (asgn.lhs, asgn.rhs, XOR);
break;
} /* eos */ } /* eos */
if(toCreate != DUMMY)
asgn.rhs = new BinaryOperator(toCreate,asgn.lhs, asgn.rhs);
icode.setAsgn(asgn.lhs, asgn.rhs); icode.setAsgn(asgn.lhs, asgn.rhs);
next1->invalidate(); next1->invalidate();
forced_finish=true; /* to exit the loop */ forced_finish=true; /* to exit the loop */
@ -398,31 +406,42 @@ int Function::findForwardLongUses(int loc_ident_idx, const ID &pLocId, iICODE be
switch (pIcode->ll()->getOpcode()) switch (pIcode->ll()->getOpcode())
{ {
case iMOV: case iMOV:
if ((pLocId.id.longId.h == pIcode->ll()->src().getReg2()) && {
(pLocId.id.longId.l == next1->ll()->src().getReg2())) const LONGID_TYPE &ref_long(pLocId.id.longId);
const LLOperand &src_op1(pIcode->ll()->src());
const LLOperand &src_op2(next1->ll()->src());
eReg srcReg1=src_op1.getReg2();
eReg srcReg2=src_op2.getReg2();
if ((ref_long.h == srcReg1) && (ref_long.l == srcReg2))
{ {
pIcode->setRegDU( next1->ll()->src().getReg2(), eUSE); pIcode->setRegDU( next1->ll()->src().getReg2(), eUSE);
asgn.rhs = COND_EXPR::idLongIdx (loc_ident_idx); asgn.rhs = AstIdent::LongIdx (loc_ident_idx);
asgn.lhs = COND_EXPR::idLong (&this->localId, DST, pIcode,HIGH_FIRST, pIcode, eDEF, *next1->ll()); asgn.lhs = AstIdent::idLong (&this->localId, DST, pIcode,HIGH_FIRST, pIcode, eDEF, *next1->ll());
pIcode->setAsgn(asgn.lhs, asgn.rhs); pIcode->setAsgn(dynamic_cast<AstIdent *>(asgn.lhs), asgn.rhs);
next1->invalidate(); next1->invalidate();
forced_finish =true; /* to exit the loop */ forced_finish =true; /* to exit the loop */
} }
break; break;
}
case iPUSH: case iPUSH:
if ((pLocId.id.longId.h == pIcode->ll()->src().getReg2()) &&
(pLocId.id.longId.l == next1->ll()->src().getReg2()))
{ {
asgn.rhs = COND_EXPR::idLongIdx (loc_ident_idx); const LONGID_TYPE &ref_long(pLocId.id.longId);
const LLOperand &src_op1(pIcode->ll()->src());
const LLOperand &src_op2(next1->ll()->src());
if ((ref_long.h == src_op1.getReg2()) &&
(ref_long.l == src_op2.getReg2()))
{
asgn.rhs = AstIdent::LongIdx (loc_ident_idx);
pIcode->setRegDU( next1->ll()->src().getReg2(), eUSE); pIcode->setRegDU( next1->ll()->src().getReg2(), eUSE);
pIcode->setUnary(HLI_PUSH, asgn.rhs); pIcode->setUnary(HLI_PUSH, asgn.rhs);
next1->invalidate(); next1->invalidate();
} }
forced_finish =true; /* to exit the loop */ forced_finish =true; /* to exit the loop */
break; break;
}
/*** others missing ****/ /*** others missing ****/
@ -432,19 +451,21 @@ int Function::findForwardLongUses(int loc_ident_idx, const ID &pLocId, iICODE be
if ((pLocId.id.longId.h == pmH->regi) && if ((pLocId.id.longId.h == pmH->regi) &&
(pLocId.id.longId.l == pmL->regi)) (pLocId.id.longId.l == pmL->regi))
{ {
asgn.lhs = COND_EXPR::idLongIdx (loc_ident_idx); asgn.lhs = AstIdent::LongIdx (loc_ident_idx);
pIcode->setRegDU( pmH->regi, USE_DEF); pIcode->setRegDU( pmH->regi, USE_DEF);
asgn.rhs = COND_EXPR::idLong (&this->localId, SRC, pIcode, asgn.rhs = AstIdent::idLong (&this->localId, SRC, pIcode,
LOW_FIRST, pIcode, eUSE, *next1->ll()); LOW_FIRST, pIcode, eUSE, *next1->ll());
condOp toCreate=DUMMY;
switch (pIcode->ll()->getOpcode()) { switch (pIcode->ll()->getOpcode()) {
case iAND: asgn.rhs = COND_EXPR::boolOp (asgn.lhs, asgn.rhs, AND); case iAND: toCreate=AND; break;
break; case iOR: toCreate=OR; break;
case iOR: asgn.rhs = COND_EXPR::boolOp (asgn.lhs, asgn.rhs, OR); case iXOR: toCreate= XOR; break;
break;
case iXOR: asgn.rhs = COND_EXPR::boolOp (asgn.lhs, asgn.rhs, XOR);
break;
} }
pIcode->setAsgn(asgn.lhs, asgn.rhs); if(DUMMY!=toCreate)
{
asgn.rhs = new BinaryOperator(toCreate,asgn.lhs, asgn.rhs);
}
pIcode->setAsgn(dynamic_cast<AstIdent *>(asgn.lhs), asgn.rhs);
next1->invalidate(); next1->invalidate();
// ftw loop restart ???? // ftw loop restart ????
//idx = 0; //idx = 0;
@ -483,9 +504,9 @@ int Function::findForwardLongUses(int loc_ident_idx, const ID &pLocId, iICODE be
{ {
if (pLocId.id.longId.srcDstRegMatch(pIcode,pIcode)) if (pLocId.id.longId.srcDstRegMatch(pIcode,pIcode))
{ {
asgn.lhs = COND_EXPR::idLongIdx (loc_ident_idx); asgn.lhs = AstIdent::LongIdx (loc_ident_idx);
asgn.rhs = COND_EXPR::idKte (0, 4); /* long 0 */ asgn.rhs = AstIdent::Kte (0, 4); /* long 0 */
asgn.lhs = COND_EXPR::boolOp (asgn.lhs, asgn.rhs, condOpJCond[next1->ll()->getOpcode() - iJB]); asgn.lhs = new BinaryOperator(condOpJCond[next1->ll()->getOpcode() - iJB],asgn.lhs, asgn.rhs);
next1->setJCond(asgn.lhs); next1->setJCond(asgn.lhs);
next1->copyDU(*pIcode, eUSE, eUSE); next1->copyDU(*pIcode, eUSE, eUSE);
pIcode->invalidate(); pIcode->invalidate();