예제 #1
0
        public override void ReplaceChild(JSNode oldChild, JSNode newChild)
        {
            if (oldChild == null)
            {
                throw new ArgumentNullException("oldChild");
            }

            if (newChild == this)
            {
                throw new InvalidOperationException("Infinite recursion");
            }

            if ((newChild != null) && !(newChild is JSExpression))
            {
                return;
            }

            var expr = (JSExpression)newChild;

            for (int i = 0, c = Values.Length; i < c; i++)
            {
                if (Values[i] == oldChild)
                {
                    Values[i] = expr;
                }
            }
        }
예제 #2
0
        public override void ReplaceChild(JSNode oldChild, JSNode newChild)
        {
            if (oldChild == null)
            {
                throw new ArgumentNullException("oldChild");
            }

            if (_Initializer == oldChild)
            {
                _Initializer = (JSStatement)newChild;
            }

            if (_Condition == oldChild)
            {
                _Condition = (JSExpression)newChild;
            }

            if (_Increment == oldChild)
            {
                _Increment = (JSStatement)newChild;
            }

            if (newChild is JSStatement)
            {
                base.ReplaceChild(oldChild, newChild);
            }
        }
예제 #3
0
파일: JSAstVisitor.cs 프로젝트: xen2/JSIL
            public NodeVisitor Get(JSNode node)
            {
                if (node == null)
                {
                    return(null);
                }

                var nodeType    = node.GetType();
                var currentType = nodeType;

                return(Cache.GetOrCreate(
                           nodeType, () => {
                    while (currentType != null)
                    {
                        NodeVisitor result;
                        if (Methods.TryGetValue(currentType, out result))
                        {
                            return result;
                        }

                        currentType = currentType.BaseType;
                    }

                    return null;
                }
                           ));
            }
예제 #4
0
파일: JSAstCursor.cs 프로젝트: ticuth/JSIL
        private IEnumerable <State> VisitNode(JSNode node, string name = null, Indices indices = null, int depth = 0)
        {
            int?statementIndex = null;

            if (indices == null)
            {
                indices = new Indices();
            }

            int nodeIndex = indices.GetNodeIndex();

            if (node is JSStatement)
            {
                statementIndex = indices.GetStatementIndex();
            }

            yield return(new State(
                             node, name, depth, nodeIndex, statementIndex
                             ));

            foreach (var e in VisitChildren(node, indices, depth))
            {
                foreach (var c in e)
                {
                    yield return(c);
                }
            }
        }
예제 #5
0
파일: JSAstCursor.cs 프로젝트: ticuth/JSIL
        public JSAstCursor(JSNode root, params string[] namesToSkip)
        {
            Root        = root;
            NamesToSkip = new HashSet <string>(namesToSkip);

            Reset();
        }
예제 #6
0
            protected VisitorCache(Type visitorType)
            {
                VisitorType = visitorType;

                var methods = new Dictionary <Type, NodeVisitor>(new ReferenceComparer <Type>());

                foreach (var m in VisitorType.GetMethods())
                {
                    if (m.Name != "VisitNode")
                    {
                        continue;
                    }

                    var parameters = m.GetParameters();
                    if (parameters.Length != 1)
                    {
                        continue;
                    }

                    var nodeType = parameters[0].ParameterType;
                    methods.Add(nodeType, MakeVisitorAdapter(m, visitorType, nodeType));
                }

                TypeToVisitor = new NodeVisitor[JSNode.NodeTypes.Length];
                foreach (var nt in JSNode.NodeTypes)
                {
                    var id = JSNode.GetTypeId(nt);
                    TypeToVisitor[id] = FindNodeVisitor(nt, methods);
                }
            }
예제 #7
0
        public override void ReplaceChild(JSNode oldChild, JSNode newChild)
        {
            if (oldChild == null)
            {
                throw new ArgumentNullException("oldChild");
            }

            var stmt = newChild as JSStatement;

            if (stmt == null)
            {
                return;
            }

            foreach (var kvp in Labels.ToArray())
            {
                if (kvp.Value == oldChild)
                {
                    if (stmt.Label == kvp.Key)
                    {
                        Labels.Replace(kvp.Key, stmt);
                    }
                    else
                    {
                        Labels.Remove(kvp.Key);

                        if (!stmt.IsNull)
                        {
                            Add(stmt);
                        }
                    }
                }
            }
        }
예제 #8
0
        public override void ReplaceChild(JSNode oldChild, JSNode newChild)
        {
            if (oldChild == null)
            {
                throw new ArgumentNullException("oldChild");
            }

            var boe = newChild as JSBinaryOperatorExpression;

            if (boe == null)
            {
                Declarations.RemoveAll((c) => c == oldChild);
            }
            else if (boe.Operator != JSOperator.Assignment)
            {
                throw new InvalidOperationException("A variable declaration statement may only contain assignments");
            }
            else
            {
                for (int i = 0, c = Declarations.Count; i < c; i++)
                {
                    if (Declarations[i] == oldChild)
                    {
                        Declarations[i] = boe;
                    }
                }
            }
        }
예제 #9
0
        public override void ReplaceChild(JSNode oldChild, JSNode newChild)
        {
            if (oldChild == null)
            {
                throw new ArgumentNullException("oldChild");
            }

            if (_Condition == oldChild)
            {
                _Condition = (JSExpression)newChild;
            }

            var cse = newChild as JSSwitchCase;

            if (cse != null)
            {
                for (int i = 0, c = Cases.Count; i < c; i++)
                {
                    if (Cases[i] == oldChild)
                    {
                        Cases[i] = cse;
                    }
                }
            }
        }
예제 #10
0
파일: JSAstCursor.cs 프로젝트: ticuth/JSIL
 public State(JSNode node, string name, int depth, int nodeIndex, int?statementIndex)
 {
     Node           = node;
     Name           = name;
     Depth          = depth;
     NodeIndex      = nodeIndex;
     StatementIndex = statementIndex;
 }
예제 #11
0
            public NodeVisitor Get(JSNode node)
            {
                if (node == null)
                {
                    return(null);
                }

                return(TypeToVisitor[node.TypeId]);
            }
예제 #12
0
        /// <summary>
        /// Responsible for traversing a node. Do not invoke directly.
        /// By default, this method traverses the node's children, but takes no other action.
        /// </summary>
        public virtual void VisitNode(JSNode node)
        {
            if (node == null)
            {
                Console.WriteLine("Warning: Null node found in JavaScript AST");
                return;
            }

            VisitChildren(node);
        }
예제 #13
0
        protected static void SetValueNames(Type nodeType, params string[] valueNames)
        {
            var id = JSNode.GetTypeId(nodeType);

            if (TypeToValueNames[id] != null)
            {
                throw new InvalidOperationException("Value names already set for this node type");
            }

            TypeToValueNames[id] = valueNames;
        }
예제 #14
0
        public override void ReplaceChild(JSNode oldChild, JSNode newChild)
        {
            if (oldChild == null)
            {
                throw new ArgumentNullException("oldChild");
            }

            throw new NotImplementedException(
                      String.Format("Statements of type '{0}' do not support child replacement", GetType().Name)
                      );
        }
예제 #15
0
        public override void ReplaceChild(JSNode oldChild, JSNode newChild)
        {
            if (newChild == this)
            {
                throw new InvalidOperationException("Direct cycle formed by replacement");
            }

            if (DefaultValue == oldChild)
            {
                DefaultValue = (JSExpression)newChild;
            }
        }
예제 #16
0
        /// <summary>
        /// Traverses all of a node's children. This is the default behavior for VisitNode.
        /// </summary>
        protected virtual void VisitChildren(JSNode node, Func <JSNode, string, bool> predicate = null)
        {
            if (node == null)
            {
                throw new ArgumentNullException("node");
            }

            var    oldPreviousSibling = PreviousSibling;
            var    oldNextSibling     = NextSibling;
            string nextSiblingName    = null;

            predicate = predicate ?? DefaultVisitPredicate;

            try {
                PreviousSibling = NextSibling = null;

                using (var e = node.Children.EnumeratorTemplate)
                    while (e.MoveNext())
                    {
                        var toVisit     = NextSibling;
                        var toVisitName = nextSiblingName;
                        NextSibling     = e.Current;
                        nextSiblingName = e.CurrentName;

                        if (toVisit != null)
                        {
                            if ((predicate == null) || predicate(toVisit, toVisitName))
                            {
                                Visit(toVisit, toVisitName);
                            }
                        }

                        PreviousSibling = toVisit;
                    }

                if (NextSibling != null)
                {
                    var toVisit = NextSibling;
                    NextSibling = null;

                    if (toVisit != null)
                    {
                        if ((predicate == null) || predicate(toVisit, nextSiblingName))
                        {
                            Visit(toVisit, nextSiblingName);
                        }
                    }
                }
            } finally {
                PreviousSibling = oldPreviousSibling;
                NextSibling     = oldNextSibling;
            }
        }
예제 #17
0
        public override void ReplaceChild(JSNode oldChild, JSNode newChild)
        {
            if (oldChild == null)
            {
                throw new ArgumentNullException("oldChild");
            }

            if (oldChild == _Expression)
            {
                _Expression = (JSExpression)newChild;
            }
        }
예제 #18
0
파일: JSLiteralTypes.cs 프로젝트: xen2/JSIL
        public override void ReplaceChild(JSNode oldChild, JSNode newChild)
        {
            foreach (var key in Variables.Keys.ToArray())
            {
                if (Variables[key] == oldChild)
                {
                    Variables[key] = (JSExpression)newChild;
                }
            }

            base.ReplaceChild(oldChild, newChild);
        }
예제 #19
0
파일: JSNodeTypes.cs 프로젝트: carcer/JSIL
        public virtual void ReplaceChildRecursive(JSNode oldChild, JSNode newChild)
        {
            ReplaceChild(oldChild, newChild);

            foreach (var child in Children)
            {
                if ((child != null) && (child != newChild))
                {
                    child.ReplaceChildRecursive(oldChild, newChild);
                }
            }
        }
예제 #20
0
        public override void ReplaceChild(JSNode oldChild, JSNode newChild)
        {
            if (oldChild == null)
            {
                throw new ArgumentNullException("oldChild");
            }

            var stmt = newChild as JSStatement;

            if (stmt == null)
            {
                return;
            }

            foreach (var kvp in Labels.ToArray())
            {
                if (kvp.Value == oldChild)
                {
                    if (stmt.Label == kvp.Key)
                    {
                        Labels.Replace(kvp.Key, stmt);
                    }
                    else if (stmt.Label == null)
                    {
                        stmt.Label = kvp.Key;

                        if (stmt.IsNull)
                        {
                            Labels.Remove(kvp.Key);
                        }
                        else
                        {
                            Labels.Replace(kvp.Key, stmt);
                        }
                    }
                    else
                    {
                        Labels.Remove(kvp.Key);

                        if (!stmt.IsNull)
                        {
                            if (Labels.ContainsKey(stmt.Label))
                            {
                                throw new InvalidOperationException("Replacing LabelGroupStatement child '" + oldChild + "' with '" + newChild + "' but group already contains the label '" + stmt.Label + "'");
                            }

                            Add(stmt);
                        }
                    }
                }
            }
        }
예제 #21
0
파일: JSAstVisitor.cs 프로젝트: ilmsg/JSIL
            public NodeVisitor Get(JSNode node)
            {
                if (node == null)
                {
                    return(null);
                }

                var nodeType = node.GetType();

                return(Cache.GetOrCreate(
                           nodeType, FindNodeVisitor
                           ));
            }
예제 #22
0
        protected static bool GetChild(JSNode parent, int index, out JSNode node, out string name)
        {
            var self = (JSLabelGroupStatement)parent;

            if (index >= self.Labels.Count)
            {
                node = null;
                name = null;
                return(false);
            }

            node = self.Labels.AtIndex(index).Value;
            name = "Labels";
            return(true);
        }
예제 #23
0
        public virtual void ReplaceChildRecursive(JSNode oldChild, JSNode newChild)
        {
            ReplaceChild(oldChild, newChild);

            using (var e = Children.EnumeratorTemplate)
                while (e.MoveNext())
                {
                    var child = e.Current;

                    if ((child != null) && (child != newChild))
                    {
                        child.ReplaceChildRecursive(oldChild, newChild);
                    }
                }
        }
예제 #24
0
        public static IEnumerable <T> GetChildNodes <T> (JSNode root, Func <T, bool> predicate = null)
            where T : JSNode
        {
            foreach (var n in root.AllChildrenRecursive)
            {
                var value = n as T;

                if (value != null)
                {
                    if ((predicate == null) || predicate(value))
                    {
                        yield return(value);
                    }
                }
            }
        }
예제 #25
0
        /// <summary>
        /// Visits a node and its children (if any), updating the traversal stack. The current node is replaced by the new node.
        /// </summary>
        /// <param name="node">The node to visit.</param>
        protected void VisitReplacement(JSNode node)
        {
            Stack.Pop();
            Stack.Push(node);

            var visitor = Visitors.Get(node);

            if (visitor != null)
            {
                visitor(this, node);
            }
            else
            {
                VisitNode(node);
            }
        }
예제 #26
0
파일: JSAstCursor.cs 프로젝트: ticuth/JSIL
        private void SkipNode(JSNode node, string name, Indices indices, int depth)
        {
            indices.GetNodeIndex();

            if (node is JSStatement)
            {
                indices.GetStatementIndex();
            }

            foreach (var e in VisitChildren(node, indices, depth))
            {
                foreach (var c in e)
                {
                    ;
                }
            }
        }
예제 #27
0
파일: JSAstCursor.cs 프로젝트: ticuth/JSIL
        private IEnumerable <IEnumerable <State> > VisitChildren(JSNode node, Indices indices, int depth)
        {
            if (node == null)
            {
                throw new ArgumentNullException("node");
            }

            JSNode nextSibling     = null;
            string nextSiblingName = null;

            int nextDepth = depth + 1;

            using (var e = node.Children.EnumeratorTemplate)
                while (e.MoveNext())
                {
                    var toVisit     = nextSibling;
                    var toVisitName = nextSiblingName;
                    nextSibling     = e.Current;
                    nextSiblingName = e.CurrentName;

                    if (toVisit != null)
                    {
                        if (toVisitName == null || !NamesToSkip.Contains(toVisitName))
                        {
                            yield return(VisitNode(toVisit, toVisitName, indices, nextDepth));
                        }
                        else
                        {
                            SkipNode(toVisit, toVisitName, indices, nextDepth);
                        }
                    }
                }

            if (nextSibling != null)
            {
                if (nextSiblingName == null || !NamesToSkip.Contains(nextSiblingName))
                {
                    yield return(VisitNode(nextSibling, nextSiblingName, indices, nextDepth));
                }
                else
                {
                    SkipNode(nextSibling, nextSiblingName, indices, nextDepth);
                }
            }
        }
예제 #28
0
파일: JSAstVisitor.cs 프로젝트: ilmsg/JSIL
        /// <summary>
        /// Visits a node and its children (if any), updating the traversal stack.
        /// </summary>
        /// <param name="node">The node to visit.</param>
        /// <param name="name">The name to annotate the node with, if any.</param>
        public void Visit(JSNode node, string name = null)
        {
            var oldNodeIndex      = NodeIndex;
            var oldStatementIndex = StatementIndex;

#if PARANOID
            if (Stack.Contains(node))
            {
                throw new InvalidOperationException("AST traversal formed a cycle");
            }
#endif

            Stack.Push(node);
            NameStack.Push(name);

            try {
                NodeIndexStack.Push(NodeIndex = NextNodeIndex);
                NextNodeIndex += 1;

                if (node is JSStatement)
                {
                    StatementIndex      = NextStatementIndex;
                    NextStatementIndex += 1;
                }

                var visitor = Visitors.Get(node);

                if (visitor != null)
                {
                    visitor(this, node);
                }
                else
                {
                    VisitNode(node);
                }
            } finally {
                NodeIndexStack.Pop();
                Stack.Pop();
                NameStack.Pop();

                NodeIndex      = oldNodeIndex;
                StatementIndex = oldStatementIndex;
            }
        }
예제 #29
0
        static bool GetValue(JSNode parent, int index, out JSNode node, out string name)
        {
            JSExpression expr   = (JSExpression)parent;
            var          values = expr.Values;

            if (index >= values.Length)
            {
                node = null;
                name = null;
                return(false);
            }
            else
            {
                node = values[index];
                name = expr.GetValueName(index) ?? "Values";

                return(true);
            }
        }
예제 #30
0
        public override void ReplaceChild(JSNode oldChild, JSNode newChild)
        {
            if (Values == null)
            {
                return;
            }

            var jse = newChild as JSExpression;

            if (jse != null)
            {
                for (var i = 0; i < Values.Length; i++)
                {
                    if (oldChild.Equals(Values[i]))
                    {
                        Values[i] = jse;
                    }
                }
            }
        }