private static void InlineBlock(SequenceStatement seq, int index)
        {
            Statement first = seq.GetStats()[index];
            Statement pre   = seq.GetStats()[index - 1];

            pre.RemoveSuccessor(pre.GetAllSuccessorEdges()[0]);
            // single regular edge
            StatEdge  edge   = first.GetPredecessorEdges(StatEdge.Type_Break)[0];
            Statement source = edge.GetSource();
            Statement parent = source.GetParent();

            source.RemoveSuccessor(edge);
            List <Statement> lst = new List <Statement>();

            for (int i = seq.GetStats().Count - 1; i >= index; i--)
            {
                lst.Add(0, seq.GetStats().RemoveAtReturningValue(i));
            }
            if (parent.type == Statement.Type_If && ((IfStatement)parent).iftype == IfStatement
                .Iftype_If && source == parent.GetFirst())
            {
                IfStatement       ifparent = (IfStatement)parent;
                SequenceStatement block    = new SequenceStatement(lst);
                block.SetAllParent();
                StatEdge newedge = new StatEdge(StatEdge.Type_Regular, source, block);
                source.AddSuccessor(newedge);
                ifparent.SetIfEdge(newedge);
                ifparent.SetIfstat(block);
                ifparent.GetStats().AddWithKey(block, block.id);
                block.SetParent(ifparent);
            }
            else
            {
                lst.Add(0, source);
                SequenceStatement block = new SequenceStatement(lst);
                block.SetAllParent();
                parent.ReplaceStatement(source, block);
                // LabelHelper.lowContinueLabels not applicable because of forward continue edges
                // LabelHelper.lowContinueLabels(block, new HashSet<StatEdge>());
                // do it by hand
                foreach (StatEdge prededge in block.GetPredecessorEdges(StatEdge.Type_Continue))
                {
                    block.RemovePredecessor(prededge);
                    prededge.GetSource().ChangeEdgeNode(Statement.Direction_Forward, prededge, source
                                                        );
                    source.AddPredecessor(prededge);
                    source.AddLabeledEdge(prededge);
                }
                if (parent.type == Statement.Type_Switch)
                {
                    ((SwitchStatement)parent).SortEdgesAndNodes();
                }
                source.AddSuccessor(new StatEdge(StatEdge.Type_Regular, source, first));
            }
        }
Ejemplo n.º 2
0
        public static void LowContinueLabels(Statement stat, HashSet <StatEdge> edges)
        {
            bool ok = (stat.type != Statement.Type_Do);

            if (!ok)
            {
                DoStatement dostat = (DoStatement)stat;
                ok = dostat.GetLooptype() == DoStatement.Loop_Do || dostat.GetLooptype() == DoStatement
                     .Loop_While || (dostat.GetLooptype() == DoStatement.Loop_For && dostat.GetIncExprent
                                         () == null);
            }
            if (ok)
            {
                Sharpen.Collections.AddAll(edges, stat.GetPredecessorEdges(StatEdge.Type_Continue
                                                                           ));
            }
            if (ok && stat.type == Statement.Type_Do)
            {
                foreach (StatEdge edge in edges)
                {
                    if (stat.ContainsStatementStrict(edge.GetSource()))
                    {
                        edge.GetDestination().RemovePredecessor(edge);
                        edge.GetSource().ChangeEdgeNode(Statement.Direction_Forward, edge, stat);
                        stat.AddPredecessor(edge);
                        stat.AddLabeledEdge(edge);
                    }
                }
            }
            foreach (Statement st in stat.GetStats())
            {
                if (st == stat.GetFirst())
                {
                    LowContinueLabels(st, edges);
                }
                else
                {
                    LowContinueLabels(st, new HashSet <StatEdge>());
                }
            }
        }
Ejemplo n.º 3
0
        public static bool SplitIrreducibleNode(Statement statement)
        {
            Statement splitnode = GetCandidateForSplitting(statement);

            if (splitnode == null)
            {
                return(false);
            }
            StatEdge enteredge = splitnode.GetPredecessorEdges(StatEdge.Type_Regular).GetEnumerator
                                     ().Current;
            // copy the smallest statement
            Statement splitcopy = CopyStatement(splitnode, null, new Dictionary <Statement, Statement
                                                                                 >());

            InitCopiedStatement(splitcopy);
            // insert the copy
            splitcopy.SetParent(statement);
            statement.GetStats().AddWithKey(splitcopy, splitcopy.id);
            // switch input edges
            foreach (StatEdge prededge in splitnode.GetPredecessorEdges(Statement.Statedge_Direct_All
                                                                        ))
            {
                if (prededge.GetSource() == enteredge.GetSource() || prededge.closure == enteredge
                    .GetSource())
                {
                    splitnode.RemovePredecessor(prededge);
                    prededge.GetSource().ChangeEdgeNode(Statement.Direction_Forward, prededge, splitcopy
                                                        );
                    splitcopy.AddPredecessor(prededge);
                }
            }
            // connect successors
            foreach (StatEdge succ in splitnode.GetSuccessorEdges(Statement.Statedge_Direct_All
                                                                  ))
            {
                splitcopy.AddSuccessor(new StatEdge(succ.GetType(), splitcopy, succ.GetDestination
                                                        (), succ.closure));
            }
            return(true);
        }
Ejemplo n.º 4
0
 private static void BuildSynchronized(Statement stat)
 {
     foreach (Statement st in stat.GetStats())
     {
         BuildSynchronized(st);
     }
     if (stat.type == Statement.Type_Sequence)
     {
         while (true)
         {
             bool             found = false;
             List <Statement> lst   = stat.GetStats();
             for (int i = 0; i < lst.Count - 1; i++)
             {
                 Statement current = lst[i];
                 // basic block
                 if (current.IsMonitorEnter())
                 {
                     Statement next       = lst[i + 1];
                     Statement nextDirect = next;
                     while (next.type == Statement.Type_Sequence)
                     {
                         next = next.GetFirst();
                     }
                     if (next.type == Statement.Type_Catchall)
                     {
                         CatchAllStatement ca = (CatchAllStatement)next;
                         if (ca.GetFirst().IsContainsMonitorExit() && ca.GetHandler().IsContainsMonitorExit
                                 ())
                         {
                             // remove the head block from sequence
                             current.RemoveSuccessor(current.GetSuccessorEdges(Statement.Statedge_Direct_All)[
                                                         0]);
                             foreach (StatEdge edge in current.GetPredecessorEdges(Statement.Statedge_Direct_All
                                                                                   ))
                             {
                                 current.RemovePredecessor(edge);
                                 edge.GetSource().ChangeEdgeNode(Statement.Direction_Forward, edge, nextDirect);
                                 nextDirect.AddPredecessor(edge);
                             }
                             stat.GetStats().RemoveWithKey(current.id);
                             stat.SetFirst(stat.GetStats()[0]);
                             // new statement
                             SynchronizedStatement sync = new SynchronizedStatement(current, ca.GetFirst(), ca
                                                                                    .GetHandler());
                             sync.SetAllParent();
                             foreach (StatEdge edge in new HashSet <StatEdge>(ca.GetLabelEdges()))
                             {
                                 sync.AddLabeledEdge(edge);
                             }
                             current.AddSuccessor(new StatEdge(StatEdge.Type_Regular, current, ca.GetFirst()));
                             ca.GetParent().ReplaceStatement(ca, sync);
                             found = true;
                             break;
                         }
                     }
                 }
             }
             if (!found)
             {
                 break;
             }
         }
     }
 }
Ejemplo n.º 5
0
        private static bool RemoveReturnCheck(Statement stat, StructMethod mt)
        {
            Statement parent = stat.GetParent();

            if (parent != null && parent.type == Statement.Type_If && stat.type == Statement.
                Type_Basicblock && stat.GetExprents().Count == 1)
            {
                Exprent exprent = stat.GetExprents()[0];
                if (exprent.type == Exprent.Exprent_Exit)
                {
                    ExitExprent exit_exprent = (ExitExprent)exprent;
                    if (exit_exprent.GetExitType() == ExitExprent.Exit_Return)
                    {
                        Exprent exprent_value = exit_exprent.GetValue();
                        //if(exprent_value.type == Exprent.EXPRENT_VAR) {
                        //	VarExprent var_value = (VarExprent)exprent_value;
                        IfStatement ifparent     = (IfStatement)parent;
                        Exprent     if_condition = ifparent.GetHeadexprent().GetCondition();
                        if (ifparent.GetElsestat() == stat && if_condition.type == Exprent.Exprent_Function &&
                            ((FunctionExprent)if_condition).GetFuncType() == FunctionExprent.Function_Eq)
                        {
                            // TODO: reversed order possible (in theory)
                            FunctionExprent func         = (FunctionExprent)if_condition;
                            Exprent         first_param  = func.GetLstOperands()[0];
                            Exprent         second_param = func.GetLstOperands()[1];
                            StatEdge        ifedge       = ifparent.GetIfEdge();
                            StatEdge        elseedge     = ifparent.GetElseEdge();
                            Statement       ifbranch     = ifparent.GetIfstat();
                            Statement       elsebranch   = ifparent.GetElsestat();
                            if (second_param.type == Exprent.Exprent_Const && second_param.GetExprType().type
                                == ICodeConstants.Type_Null)
                            {
                                // TODO: reversed parameter order
                                //if(first_param.type == Exprent.EXPRENT_VAR && ((VarExprent)first_param).getIndex() == var_value.getIndex()) {
                                if (first_param.Equals(exprent_value))
                                {
                                    // TODO: check for absence of side effects like method invocations etc.
                                    if (ifbranch.type == Statement.Type_Basicblock && ifbranch.GetExprents().Count ==
                                        1 && ifbranch.GetExprents()[0].type == Exprent.Exprent_Exit)
                                    {
                                        // TODO: special check for IllegalStateException
                                        ifparent.GetFirst().RemoveSuccessor(ifedge);
                                        ifparent.GetFirst().RemoveSuccessor(elseedge);
                                        ifparent.GetStats().RemoveWithKey(ifbranch.id);
                                        ifparent.GetStats().RemoveWithKey(elsebranch.id);
                                        if (!(ifbranch.GetAllSuccessorEdges().Count == 0))
                                        {
                                            ifbranch.RemoveSuccessor(ifbranch.GetAllSuccessorEdges()[0]);
                                        }
                                        if (!(ifparent.GetFirst().GetExprents().Count == 0))
                                        {
                                            elsebranch.GetExprents().InsertRange(0, ifparent.GetFirst().GetExprents());
                                        }
                                        ifparent.GetParent().ReplaceStatement(ifparent, elsebranch);
                                        ifparent.GetParent().SetAllParent();
                                        return(true);
                                    }
                                }
                            }
                        }
                    }
                }
            }
            else if (parent != null && parent.type == Statement.Type_Sequence && stat.type ==
                     Statement.Type_Basicblock && stat.GetExprents().Count == 1)
            {
                //}
                Exprent exprent = stat.GetExprents()[0];
                if (exprent.type == Exprent.Exprent_Exit)
                {
                    ExitExprent exit_exprent = (ExitExprent)exprent;
                    if (exit_exprent.GetExitType() == ExitExprent.Exit_Return)
                    {
                        Exprent           exprent_value = exit_exprent.GetValue();
                        SequenceStatement sequence      = (SequenceStatement)parent;
                        int sequence_stats_number       = sequence.GetStats().Count;
                        if (sequence_stats_number > 1 && sequence.GetStats().GetLast() == stat && sequence
                            .GetStats()[sequence_stats_number - 2].type == Statement.Type_If)
                        {
                            IfStatement ifstat       = (IfStatement)sequence.GetStats()[sequence_stats_number - 2];
                            Exprent     if_condition = ifstat.GetHeadexprent().GetCondition();
                            if (ifstat.iftype == IfStatement.Iftype_If && if_condition.type == Exprent.Exprent_Function &&
                                ((FunctionExprent)if_condition).GetFuncType() == FunctionExprent.Function_Eq)
                            {
                                // TODO: reversed order possible (in theory)
                                FunctionExprent func         = (FunctionExprent)if_condition;
                                Exprent         first_param  = func.GetLstOperands()[0];
                                Exprent         second_param = func.GetLstOperands()[1];
                                Statement       ifbranch     = ifstat.GetIfstat();
                                if (second_param.type == Exprent.Exprent_Const && second_param.GetExprType().type
                                    == ICodeConstants.Type_Null)
                                {
                                    // TODO: reversed parameter order
                                    if (first_param.Equals(exprent_value))
                                    {
                                        // TODO: check for absence of side effects like method invocations etc.
                                        if (ifbranch.type == Statement.Type_Basicblock && ifbranch.GetExprents().Count ==
                                            1 && ifbranch.GetExprents()[0].type == Exprent.Exprent_Exit)
                                        {
                                            // TODO: special check for IllegalStateException
                                            ifstat.RemoveSuccessor(ifstat.GetAllSuccessorEdges()[0]);
                                            // remove 'else' edge
                                            if (!(ifstat.GetFirst().GetExprents().Count == 0))
                                            {
                                                stat.GetExprents().InsertRange(0, ifstat.GetFirst().GetExprents());
                                            }
                                            foreach (StatEdge edge in ifstat.GetAllPredecessorEdges())
                                            {
                                                ifstat.RemovePredecessor(edge);
                                                edge.GetSource().ChangeEdgeNode(Statement.Direction_Forward, edge, stat);
                                                stat.AddPredecessor(edge);
                                            }
                                            sequence.GetStats().RemoveWithKey(ifstat.id);
                                            sequence.SetFirst(sequence.GetStats()[0]);
                                            return(true);
                                        }
                                    }
                                }
                            }
                        }
                    }
                }
            }
            foreach (Statement st in stat.GetStats())
            {
                if (RemoveReturnCheck(st, mt))
                {
                    return(true);
                }
            }
            return(false);
        }
Ejemplo n.º 6
0
 private static void CondenseSequencesRec(Statement stat)
 {
     if (stat.type == Statement.Type_Sequence)
     {
         List <Statement> lst      = new List <Statement>(stat.GetStats());
         bool             unfolded = false;
         // unfold blocks
         for (int i = 0; i < lst.Count; i++)
         {
             Statement st = lst[i];
             if (st.type == Statement.Type_Sequence)
             {
                 RemoveEmptyStatements((SequenceStatement)st);
                 if (i == lst.Count - 1 || IsSequenceDisbandable(st, lst[i + 1]))
                 {
                     // move predecessors
                     Statement first = st.GetFirst();
                     foreach (StatEdge edge in st.GetAllPredecessorEdges())
                     {
                         st.RemovePredecessor(edge);
                         edge.GetSource().ChangeEdgeNode(Statement.Direction_Forward, edge, first);
                         first.AddPredecessor(edge);
                     }
                     // move successors
                     Statement last = st.GetStats().GetLast();
                     if ((last.GetAllSuccessorEdges().Count == 0) && i < lst.Count - 1)
                     {
                         last.AddSuccessor(new StatEdge(StatEdge.Type_Regular, last, lst[i + 1]));
                     }
                     else
                     {
                         foreach (StatEdge edge in last.GetAllSuccessorEdges())
                         {
                             if (i == lst.Count - 1)
                             {
                                 if (edge.closure == st)
                                 {
                                     stat.AddLabeledEdge(edge);
                                 }
                             }
                             else
                             {
                                 edge.GetSource().ChangeEdgeType(Statement.Direction_Forward, edge, StatEdge.Type_Regular
                                                                 );
                                 edge.closure.GetLabelEdges().Remove(edge);
                                 edge.closure = null;
                             }
                         }
                     }
                     foreach (StatEdge edge in st.GetAllSuccessorEdges())
                     {
                         st.RemoveSuccessor(edge);
                     }
                     foreach (StatEdge edge in new HashSet <StatEdge>(st.GetLabelEdges()))
                     {
                         if (edge.GetSource() != last)
                         {
                             last.AddLabeledEdge(edge);
                         }
                     }
                     lst.RemoveAtReturningValue(i);
                     lst.InsertRange(i, st.GetStats());
                     i--;
                     unfolded = true;
                 }
             }
         }
         if (unfolded)
         {
             SequenceStatement sequence = new SequenceStatement(lst);
             sequence.SetAllParent();
             stat.GetParent().ReplaceStatement(stat, sequence);
             stat = sequence;
         }
     }
     // sequence consisting of one statement -> disband
     if (stat.type == Statement.Type_Sequence)
     {
         RemoveEmptyStatements((SequenceStatement)stat);
         if (stat.GetStats().Count == 1)
         {
             Statement st = stat.GetFirst();
             bool      ok = (st.GetAllSuccessorEdges().Count == 0);
             if (!ok)
             {
                 StatEdge edge = st.GetAllSuccessorEdges()[0];
                 ok = (stat.GetAllSuccessorEdges().Count == 0);
                 if (!ok)
                 {
                     StatEdge statedge = stat.GetAllSuccessorEdges()[0];
                     ok = (edge.GetDestination() == statedge.GetDestination());
                     if (ok)
                     {
                         st.RemoveSuccessor(edge);
                     }
                 }
             }
             if (ok)
             {
                 stat.GetParent().ReplaceStatement(stat, st);
                 stat = st;
             }
         }
     }
     // replace flat statements with synthetic basic blocks
     while (true)
     {
         foreach (Statement st in stat.GetStats())
         {
             if (((st.GetStats().Count == 0) || st.GetExprents() != null) && st.type != Statement
                 .Type_Basicblock)
             {
                 DestroyAndFlattenStatement(st);
                 goto outer_continue;
             }
         }
         break;
         outer_continue :;
     }
     outer_break :;
     // recursion
     for (int i = 0; i < stat.GetStats().Count; i++)
     {
         CondenseSequencesRec(stat.GetStats()[i]);
     }
 }
Ejemplo n.º 7
0
        private static int IntegrateExits(Statement stat)
        {
            int       ret = 0;
            Statement dest;

            if (stat.GetExprents() == null)
            {
                while (true)
                {
                    int changed = 0;
                    foreach (Statement st in stat.GetStats())
                    {
                        changed = IntegrateExits(st);
                        if (changed > 0)
                        {
                            ret = 1;
                            break;
                        }
                    }
                    if (changed == 0)
                    {
                        break;
                    }
                }
                if (stat.type == Statement.Type_If)
                {
                    IfStatement ifst = (IfStatement)stat;
                    if (ifst.GetIfstat() == null)
                    {
                        StatEdge ifedge = ifst.GetIfEdge();
                        dest = IsExitEdge(ifedge);
                        if (dest != null)
                        {
                            BasicBlockStatement bstat = new BasicBlockStatement(new BasicBlock(DecompilerContext
                                                                                               .GetCounterContainer().GetCounterAndIncrement(CounterContainer.Statement_Counter
                                                                                                                                             )));
                            bstat.SetExprents(DecHelper.CopyExprentList(dest.GetExprents()));
                            ifst.GetFirst().RemoveSuccessor(ifedge);
                            StatEdge newedge = new StatEdge(StatEdge.Type_Regular, ifst.GetFirst(), bstat);
                            ifst.GetFirst().AddSuccessor(newedge);
                            ifst.SetIfEdge(newedge);
                            ifst.SetIfstat(bstat);
                            ifst.GetStats().AddWithKey(bstat, bstat.id);
                            bstat.SetParent(ifst);
                            StatEdge oldexitedge = dest.GetAllSuccessorEdges()[0];
                            StatEdge newexitedge = new StatEdge(StatEdge.Type_Break, bstat, oldexitedge.GetDestination
                                                                    ());
                            bstat.AddSuccessor(newexitedge);
                            oldexitedge.closure.AddLabeledEdge(newexitedge);
                            ret = 1;
                        }
                    }
                }
            }
            if (stat.GetAllSuccessorEdges().Count == 1 && stat.GetAllSuccessorEdges()[0].GetType
                    () == StatEdge.Type_Break && (stat.GetLabelEdges().Count == 0))
            {
                Statement parent = stat.GetParent();
                if (stat != parent.GetFirst() || (parent.type != Statement.Type_If && parent.type
                                                  != Statement.Type_Switch))
                {
                    StatEdge destedge = stat.GetAllSuccessorEdges()[0];
                    dest = IsExitEdge(destedge);
                    if (dest != null)
                    {
                        stat.RemoveSuccessor(destedge);
                        BasicBlockStatement bstat = new BasicBlockStatement(new BasicBlock(DecompilerContext
                                                                                           .GetCounterContainer().GetCounterAndIncrement(CounterContainer.Statement_Counter
                                                                                                                                         )));
                        bstat.SetExprents(DecHelper.CopyExprentList(dest.GetExprents()));
                        StatEdge oldexitedge = dest.GetAllSuccessorEdges()[0];
                        StatEdge newexitedge = new StatEdge(StatEdge.Type_Break, bstat, oldexitedge.GetDestination
                                                                ());
                        bstat.AddSuccessor(newexitedge);
                        oldexitedge.closure.AddLabeledEdge(newexitedge);
                        SequenceStatement block = new SequenceStatement(Sharpen.Arrays.AsList(stat, bstat
                                                                                              ));
                        block.SetAllParent();
                        parent.ReplaceStatement(stat, block);
                        // LabelHelper.lowContinueLabels not applicable because of forward continue edges
                        // LabelHelper.lowContinueLabels(block, new HashSet<StatEdge>());
                        // do it by hand
                        foreach (StatEdge prededge in block.GetPredecessorEdges(StatEdge.Type_Continue))
                        {
                            block.RemovePredecessor(prededge);
                            prededge.GetSource().ChangeEdgeNode(Statement.Direction_Forward, prededge, stat);
                            stat.AddPredecessor(prededge);
                            stat.AddLabeledEdge(prededge);
                        }
                        stat.AddSuccessor(new StatEdge(StatEdge.Type_Regular, stat, bstat));
                        foreach (StatEdge edge in dest.GetAllPredecessorEdges())
                        {
                            if (!edge.@explicit && stat.ContainsStatementStrict(edge.GetSource()) && MergeHelper
                                .IsDirectPath(edge.GetSource().GetParent(), bstat))
                            {
                                dest.RemovePredecessor(edge);
                                edge.GetSource().ChangeEdgeNode(Statement.Direction_Forward, edge, bstat);
                                bstat.AddPredecessor(edge);
                                if (!stat.ContainsStatementStrict(edge.closure))
                                {
                                    stat.AddLabeledEdge(edge);
                                }
                            }
                        }
                        ret = 2;
                    }
                }
            }
            return(ret);
        }