コード例 #1
0
        private string AdjustGoto(IlIns il, bool isDecompile)
        {
            long   lv    = IlIns.LabelToValue(il.Value);
            string label = null;

            if (switchBlocks.ContainsKey(lv))
            {
                FlowGraphNode gnode = switchBlocks[lv];
                DAGNode       dnode = switchExpressions[gnode.EndLabelValue];
                while (dnode is ReferenceNode)
                {
                    dnode = dnode.NextNodes[0];
                }
                if (dnode is LeafNode)
                {
                    DAGNode r = GetVarReference(dnode.Data);
                    if (r != null)
                    {
                        int           v        = (int)ConstUtility.ParseLong(r.Data);
                        IlIns         switchIl = ilLines[gnode.EndLabelValue];
                        SwitchOperand op       = switchIl.Operand as SwitchOperand;
                        if (v >= 0 && v < op.Labels.Count)
                        {
                            label = op.Labels[v];
                            lv    = IlIns.LabelToValue(op.Labels[v]);
                        }
                    }
                }
            }
            string label2 = AdjustGoto(il.LabelValue, lv, isDecompile);

            if (label2 != null)
            {
                return(label2);
            }
            else if (label != null)
            {
                return(label);
            }
            return(null);
        }
コード例 #2
0
        private string AdjustGoto(long srcLv, long _destLv, bool isDecompile)
        {
            string label  = null;
            long   destLv = _destLv;

            for (;;)
            {
                int    ix  = ilLines.Keys.IndexOf(destLv);
                IlIns  il  = ilLines.Values[ix];
                OpCode opc = IlOpcodes.Get(il.Opcode);
                if (opc == OpCodes.Br || opc == OpCodes.Br_S)
                {
                    label  = il.Value;
                    destLv = IlIns.LabelToValue(il.Value);
                }
                else
                {
                    break;
                }
            }
            EHBlockNode ns = rootEHNode.Find(srcLv);
            EHBlockNode nd = ns.Find(destLv);

            if (nd != null && ns != nd)
            {
                EHBlockNode d = nd;
                while (d != null && ns != d.EncloseBlock.EncloseNode)
                {
                    d = d.EncloseBlock.EncloseNode;
                }
                return("IL_" + d.ScopeStart.ToString("X6"));
            }
            if (label != null)
            {
                return(label);
            }
            return(null);
        }
コード例 #3
0
        private void AdjustFlowGraph()
        {
            flowGraph.Reset();
            for (; flowGraph.CurNode != null; flowGraph.Next())
            {
                FlowGraphNode node = flowGraph.CurNode;
                int           i    = ilLines.Keys.IndexOf(node.LabelValue);
                for (; i < ilLines.Values.Count; i++)
                {
                    IlIns il = ilLines.Values[i];
                    if (il.LabelValue == node.LabelValue)
                    {
                        BeginGraphNode(node);
                    }
                    else if (il.LabelValue != node.LabelValue && flowGraph.IsNode(il.LabelValue))
                    {
                        //行进到块的开始语句才发现新开始块是异常构造块或跳转目标倒致的块
                        EndGraphNode(node, false);
                        break;
                    }
                    IlOpcode op0 = IlOpcodes.GetEH(il.Opcode);
                    if (op0 != IlOpcode.Prefixref)
                    {
                        EvaluateEH(op0, il, false);
                    }
                    else
                    {
                        OpCode op   = IlOpcodes.Get(il.Opcode);
                        int    type = EvaluateIl(op, il, false);
                        switch (type)
                        {
                        case -2:    //永不成立的条件跳转,当前结点与分支目标块断开
                        {
                            long target = IlIns.LabelToValue(il.Value);
                            if (flowGraph.IsNode(target))
                            {
                                FlowGraphNode n = flowGraph[target];
                                node.DelNext(n);
                            }
                            EndGraphNode(node, false);
                        }
                        break;

                        case -1:    //永成立的条件跳转,当前结点与下一条指令开始的块断开
                        {
                            if (i + 1 < ilLines.Values.Count)
                            {
                                if (flowGraph.IsNode(ilLines.Values[i + 1].LabelValue))
                                {
                                    FlowGraphNode n = flowGraph[ilLines.Values[i + 1].LabelValue];
                                    node.DelNext(n);
                                }
                            }
                            EndGraphNode(node, false);
                        }
                        break;

                        case 0:    //正常指令流
                        {
                        }
                        break;

                        case 1:    //无条件跳转
                        case 2:    //条件跳转
                        case 3:    //switch分支
                        {
                            EndGraphNode(node, false);
                        }
                        break;

                        case 4:    //结束类语句
                        {
                            EndGraphNode(node, false);
                        }
                        break;
                        }
                        if (type != 0)
                        {
                            break;
                        }
                    }
                }
            }
            //合并无分支的顺序块
            flowGraph.Reset();
            for (; flowGraph.CurNode != null; flowGraph.Next())
            {
                FlowGraphNode node = flowGraph.CurNode;
                while (node.NextNodes.Count == 1 && node.NextNodes[0].PrevNodes.Count == 1)
                {
                    FlowGraphNode n = node.NextNodes[0];
                    int           i = ilLines.Keys.IndexOf(node.EndLabelValue);
                    int           j = ilLines.Keys.IndexOf(n.LabelValue);
                    if (i + 1 == j)
                    {
                        flowGraph.Combine(node, n);
                    }
                    else
                    {
                        break;
                    }
                }
            }
        }
コード例 #4
0
        private void BuildFlowGraph()
        {
            flowGraph = new FlowGraph();
            FlowGraphNode curNode     = null;
            FlowGraphNode prevNode    = null;
            bool          nextIsBlock = true;

            for (int i = 0; i < ilLines.Count; i++)
            {
                IlIns il = ilLines.Values[i];
                if (nextIsBlock)
                {
                    nextIsBlock = false;
                    FlowGraphNode node = flowGraph.NewNode(il.LabelValue);
                    curNode = node;
                    if (prevNode != null)
                    {
                        prevNode.AddNext(node);
                    }
                }
                else
                {
                    if (flowGraph.IsNode(il.LabelValue))
                    {
                        FlowGraphNode node = flowGraph[il.LabelValue];
                        curNode.EndLabelValue = GetPrevIlLabelValue(il.LabelValue);
                        curNode.AddNext(node);
                        curNode = node;
                    }
                }
                IlOpcode op0 = IlOpcodes.GetEH(il.Opcode);
                if (op0 != IlOpcode.Prefixref)
                {
                    switch (op0)
                    {
                    case IlOpcode.TRY:
                    {
                        FlowGraphNode node = flowGraph.NewNode(il.LabelValue);
                        if (curNode != null)
                        {
                            curNode.AddNext(node);
                        }
                        curNode = node;
                    }
                    break;

                    case IlOpcode.CATCH:
                    {
                        FlowGraphNode node = flowGraph.NewNode(il.LabelValue);
                        curNode = node;
                    }
                    break;

                    case IlOpcode.FINALLY:
                    {
                        FlowGraphNode node = flowGraph.NewNode(il.LabelValue);
                        curNode = node;
                    }
                    break;

                    case IlOpcode.FILTER:
                    {
                        FlowGraphNode node = flowGraph.NewNode(il.LabelValue);
                        curNode = node;
                    }
                    break;

                    case IlOpcode.FAULT:
                    {
                        FlowGraphNode node = flowGraph.NewNode(il.LabelValue);
                        curNode = node;
                    }
                    break;

                    case IlOpcode.ENDTRY:
                    case IlOpcode.ENDCATCH:
                    case IlOpcode.ENDFINALLY:
                    case IlOpcode.ENDFILTER:
                    case IlOpcode.ENDFAULT:
                    {
                        curNode.EndLabelValue = il.LabelValue;
                        prevNode    = null;
                        nextIsBlock = true;
                    }
                    break;
                    }
                }
                else
                {
                    OpCode op = IlOpcodes.Get(il.Opcode);
                    switch ((IlOpcode)op.Value)
                    {
                    case IlOpcode.Br:
                    case IlOpcode.Br_S:
                    {
                        long          val  = IlIns.LabelToValue(il.Value);
                        FlowGraphNode node = null;
                        if (val > il.LabelValue)
                        {
                            node = flowGraph.NewNode(val);
                            curNode.AddNext(node);
                        }
                        else
                        {
                            long          prevVal = GetPrevIlLabelValue(val);
                            FlowGraphNode d       = flowGraph.Find(val);
                            node = flowGraph.Split(val, prevVal);
                            if (curNode != d)
                            {
                                curNode.AddNext(node);
                            }
                            else
                            {
                                node.AddNext(node);
                                curNode = node;
                            }
                        }
                        curNode.EndLabelValue = il.LabelValue;
                        prevNode    = null;
                        nextIsBlock = true;
                    }
                    break;

                    case IlOpcode.Brtrue:
                    case IlOpcode.Brfalse:
                    case IlOpcode.Brtrue_S:
                    case IlOpcode.Brfalse_S:
                    case IlOpcode.Beq_S:
                    case IlOpcode.Bge_S:
                    case IlOpcode.Bgt_S:
                    case IlOpcode.Ble_S:
                    case IlOpcode.Blt_S:
                    case IlOpcode.Bne_Un_S:
                    case IlOpcode.Bge_Un_S:
                    case IlOpcode.Bgt_Un_S:
                    case IlOpcode.Ble_Un_S:
                    case IlOpcode.Blt_Un_S:
                    case IlOpcode.Beq:
                    case IlOpcode.Bge:
                    case IlOpcode.Bgt:
                    case IlOpcode.Ble:
                    case IlOpcode.Blt:
                    case IlOpcode.Bne_Un:
                    case IlOpcode.Bge_Un:
                    case IlOpcode.Bgt_Un:
                    case IlOpcode.Ble_Un:
                    case IlOpcode.Blt_Un:
                    {
                        long          val  = IlIns.LabelToValue(il.Value);
                        FlowGraphNode node = null;
                        if (val > il.LabelValue)
                        {
                            node = flowGraph.NewNode(val);
                            curNode.AddNext(node);
                        }
                        else
                        {
                            long          prevVal = GetPrevIlLabelValue(val);
                            FlowGraphNode d       = flowGraph.Find(val);
                            node = flowGraph.Split(val, prevVal);
                            if (curNode != d)
                            {
                                curNode.AddNext(node);
                            }
                            else
                            {
                                node.AddNext(node);
                                curNode = node;
                            }
                        }
                        curNode.EndLabelValue = il.LabelValue;
                        prevNode    = curNode;
                        nextIsBlock = true;
                    }
                    break;

                    case IlOpcode.Switch:
                    {
                        SwitchOperand opVal = il.Operand as SwitchOperand;
                        foreach (string label in opVal.Labels)
                        {
                            long          val  = IlIns.LabelToValue(label);
                            FlowGraphNode node = null;
                            if (val > il.LabelValue)
                            {
                                node = flowGraph.NewNode(val);
                                curNode.AddNext(node);
                            }
                            else
                            {
                                long          prevVal = GetPrevIlLabelValue(val);
                                FlowGraphNode d       = flowGraph.Find(val);
                                node = flowGraph.Split(val, prevVal);
                                if (curNode != d)
                                {
                                    curNode.AddNext(node);
                                }
                                else
                                {
                                    node.AddNext(node);
                                    curNode = node;
                                }
                            }
                        }
                        curNode.EndLabelValue = il.LabelValue;
                        prevNode    = curNode;
                        nextIsBlock = true;
                    }
                    break;

                    case IlOpcode.Ret:
                    case IlOpcode.Break:
                    case IlOpcode.Throw:
                    case IlOpcode.Rethrow:
                    case IlOpcode.Leave:
                    case IlOpcode.Leave_S:
                    case IlOpcode.Endfilter:
                    case IlOpcode.Endfinally:
                    {
                        curNode.EndLabelValue = il.LabelValue;
                        prevNode    = null;
                        nextIsBlock = true;
                    }
                    break;
                    }
                }
            }
        }