Browse Source

Using boost now

Artur K 12 years ago
parent
commit
4dd97b0709
16 changed files with 548 additions and 432 deletions
  1. 29 14
      include/BasicBlock.h
  2. 12 6
      include/Procedure.h
  3. 5 5
      include/ast.h
  4. 1 0
      include/bundle.h
  5. 1 0
      include/graph.h
  6. 16 0
      include/icode.h
  7. 9 4
      include/locident.h
  8. 1 1
      include/symtab.h
  9. 116 84
      src/BasicBlock.cpp
  10. 2 2
      src/ast.cpp
  11. 4 1
      src/control.cpp
  12. 281 272
      src/dataflow.cpp
  13. 40 30
      src/graph.cpp
  14. 8 0
      src/icode.cpp
  15. 6 1
      src/locident.cpp
  16. 17 12
      src/procs.cpp

+ 29 - 14
include/BasicBlock.h

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

+ 12 - 6
include/Procedure.h

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

+ 5 - 5
include/ast.h

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

+ 1 - 0
include/bundle.h

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

+ 1 - 0
include/graph.h

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

+ 16 - 0
include/icode.h

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

+ 9 - 4
include/locident.h

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

+ 1 - 1
include/symtab.h

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

+ 116 - 84
src/BasicBlock.cpp

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

+ 2 - 2
src/ast.cpp

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

+ 4 - 1
src/control.cpp

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

+ 281 - 272
src/dataflow.cpp

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

+ 40 - 30
src/graph.cpp

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

+ 8 - 0
src/icode.cpp

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

+ 6 - 1
src/locident.cpp

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

+ 17 - 12
src/procs.cpp

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