예제 #1
0
 static void Validate(ScopeBlock scope)
 {
     scope.Validate();
     foreach (var child in scope.Children)
     {
         Validate(child);
     }
 }
예제 #2
0
        private void PostProcessMethod(MethodDef method, bool isExport)
        {
            CFG.ScopeBlock scope = this.Runtime.LookupMethod(method);

            var ilTransformer = new ILPostTransformer(method, scope, this.Runtime);

            ilTransformer.Transform();
        }
예제 #3
0
 static void AddScopeBlock(ScopeBlock block, ScopeBlock child)
 {
     if (block.Content.Count > 0)
     {
         var newScope = new ScopeBlock();
         foreach (var instrBlock in block.Content)
         {
             newScope.Content.Add(instrBlock);
         }
         block.Content.Clear();
         block.Children.Add(newScope);
     }
     block.Children.Add(child);
 }
예제 #4
0
 static void AddBasicBlock(ScopeBlock block, BasicBlock <CILInstrList> child)
 {
     if (block.Children.Count > 0)
     {
         var last = block.Children.Last();
         if (last.Type != ScopeType.None)
         {
             last = new ScopeBlock();
             block.Children.Add(last);
         }
         block = last;
     }
     Debug.Assert(block.Children.Count == 0);
     block.Content.Add(child);
 }
예제 #5
0
 private static bool SearchBlockInternal(ScopeBlock scope, IBasicBlock target, Stack <ScopeBlock> scopeStack)
 {
     if (scope.Content.Count > 0)
     {
         if (scope.Content.Contains(target))
         {
             scopeStack.Push(scope);
             return(true);
         }
         return(false);
     }
     scopeStack.Push(scope);
     foreach (var child in scope.Children)
     {
         if (SearchBlockInternal(child, target, scopeStack))
         {
             return(true);
         }
     }
     scopeStack.Pop();
     return(false);
 }
예제 #6
0
        static ScopeBlock AssignScopes(CilBody body, List <BasicBlock <CILInstrList> > blocks)
        {
            var ehScopes = new Dictionary <ExceptionHandler, Tuple <ScopeBlock, ScopeBlock, ScopeBlock> >();

            foreach (var eh in body.ExceptionHandlers)
            {
                var tryBlock     = new ScopeBlock(ScopeType.Try, eh);
                var handlerBlock = new ScopeBlock(ScopeType.Handler, eh);

                if (eh.FilterStart != null)
                {
                    var filterBlock = new ScopeBlock(ScopeType.Filter, eh);
                    ehScopes[eh] = Tuple.Create(tryBlock, handlerBlock, filterBlock);
                }
                else
                {
                    ehScopes[eh] = Tuple.Create(tryBlock, handlerBlock, (ScopeBlock)null);
                }
            }

            var root       = new ScopeBlock();
            var scopeStack = new Stack <ScopeBlock>();

            scopeStack.Push(root);

            foreach (var block in blocks)
            {
                var header = block.Content[0];

                foreach (ExceptionHandler eh in body.ExceptionHandlers)
                {
                    Tuple <ScopeBlock, ScopeBlock, ScopeBlock> ehScope = ehScopes[eh];

                    if (header == eh.TryEnd)
                    {
                        var pop = scopeStack.Pop();
                        Debug.Assert(pop == ehScope.Item1);
                    }

                    if (header == eh.HandlerEnd)
                    {
                        var pop = scopeStack.Pop();
                        Debug.Assert(pop == ehScope.Item2);
                    }

                    if (eh.FilterStart != null && header == eh.HandlerStart)
                    {
                        // Filter must precede handler immediately
                        Debug.Assert(scopeStack.Peek().Type == ScopeType.Filter);
                        var pop = scopeStack.Pop();
                        Debug.Assert(pop == ehScope.Item3);
                    }
                }
                foreach (ExceptionHandler eh in body.ExceptionHandlers.Reverse())
                {
                    Tuple <ScopeBlock, ScopeBlock, ScopeBlock> ehScope = ehScopes[eh];
                    ScopeBlock parent = scopeStack.Count > 0 ? scopeStack.Peek() : null;

                    if (header == eh.TryStart)
                    {
                        if (parent != null)
                        {
                            AddScopeBlock(parent, ehScope.Item1);
                        }
                        scopeStack.Push(ehScope.Item1);
                    }

                    if (header == eh.HandlerStart)
                    {
                        if (parent != null)
                        {
                            AddScopeBlock(parent, ehScope.Item2);
                        }
                        scopeStack.Push(ehScope.Item2);
                    }

                    if (header == eh.FilterStart)
                    {
                        if (parent != null)
                        {
                            AddScopeBlock(parent, ehScope.Item3);
                        }
                        scopeStack.Push(ehScope.Item3);
                    }
                }

                ScopeBlock scope = scopeStack.Peek();
                AddBasicBlock(scope, block);
            }
            foreach (ExceptionHandler eh in body.ExceptionHandlers)
            {
                if (eh.TryEnd == null)
                {
                    var pop = scopeStack.Pop();
                    Debug.Assert(pop == ehScopes[eh].Item1);
                }
                if (eh.HandlerEnd == null)
                {
                    var pop = scopeStack.Pop();
                    Debug.Assert(pop == ehScopes[eh].Item2);
                }
            }
            Debug.Assert(scopeStack.Count == 1);
            Validate(root);

            return(root);
        }