/// <summary>
        /// Visits a group level declaration.
        /// </summary>
        private void VisitGroupLevelDeclaration(StateGroupDeclaration parentNode, TokenRange tokenRange)
        {
            ModifierSet modSet = ModifierSet.CreateDefault();

            while (!this.TokenStream.Done &&
                   this.TokenStream.Peek().Type != TokenType.StateDecl &&
                   this.TokenStream.Peek().Type != TokenType.StateGroupDecl &&
                   this.TokenStream.Peek().Type != TokenType.MachineDecl)
            {
                new ModifierVisitor(this.TokenStream).Visit(modSet);

                this.TokenStream.Index++;
                this.TokenStream.SkipWhiteSpaceAndCommentTokens();
            }

            if (this.TokenStream.Done ||
                (this.TokenStream.Peek().Type != TokenType.StateDecl &&
                 this.TokenStream.Peek().Type != TokenType.StateGroupDecl))
            {
                throw new ParsingException("Expected state or group declaration.", this.TokenStream.Peek(), TokenType.StateDecl, TokenType.StateGroupDecl);
            }

            if (this.TokenStream.Peek().Type == TokenType.StateDecl)
            {
                new StateDeclarationVisitor(this.TokenStream).Visit(parentNode.Machine, parentNode, modSet, tokenRange.Start());
            }
            else if (this.TokenStream.Peek().Type == TokenType.StateGroupDecl)
            {
                new StateGroupDeclarationVisitor(this.TokenStream).Visit(parentNode.Machine, parentNode, modSet, tokenRange.Start());
            }
        }
Beispiel #2
0
        internal void VisitExternDeclaration(NamespaceDeclaration namespaceNode, MachineDeclaration machineNode)
        {
            // Skip over "extern".
            this.TokenStream.Index++;
            this.TokenStream.SkipWhiteSpaceAndCommentTokens();

            if (this.TokenStream.Done ||
                this.TokenStream.Peek().Type != TokenType.EventDecl)
            {
                throw new ParsingException("\"extern\" applies only to events and can have no access modifiers.", this.TokenStream.Peek(), TokenType.EventDecl);
            }

            this.VisitEventDeclaration(namespaceNode, machineNode, ModifierSet.CreateDefault(), isExtern: true);
        }
Beispiel #3
0
        /// <summary>
        /// Visits an event or machine declaration.
        /// </summary>
        /// <param name="parentNode">Node</param>
        private void VisitEventOrMachineDeclaration(NamespaceDeclaration parentNode)
        {
            ModifierSet modSet = ModifierSet.CreateDefault();

            while (!base.TokenStream.Done &&
                   base.TokenStream.Peek().Type != TokenType.EventDecl &&
                   base.TokenStream.Peek().Type != TokenType.MachineDecl &&
                   base.TokenStream.Peek().Type != TokenType.Monitor)
            {
                new ModifierVisitor(base.TokenStream).Visit(modSet);

                base.TokenStream.Index++;
                base.TokenStream.SkipWhiteSpaceAndCommentTokens();
            }

            if (base.TokenStream.Done ||
                (base.TokenStream.Peek().Type != TokenType.EventDecl &&
                 base.TokenStream.Peek().Type != TokenType.MachineDecl &&
                 base.TokenStream.Peek().Type != TokenType.Monitor))
            {
                throw new ParsingException("Expected event, machine or monitor declaration.",
                                           new List <TokenType>
                {
                    TokenType.EventDecl,
                    TokenType.MachineDecl,
                    TokenType.Monitor
                });
            }

            if (base.TokenStream.Peek().Type == TokenType.EventDecl)
            {
                new EventDeclarationVisitor(base.TokenStream).Visit(parentNode, null, modSet);
            }
            else if (base.TokenStream.Peek().Type == TokenType.MachineDecl)
            {
                new MachineDeclarationVisitor(base.TokenStream).Visit(null, parentNode, false, modSet);
            }
            else if (base.TokenStream.Peek().Type == TokenType.Monitor)
            {
                new MachineDeclarationVisitor(base.TokenStream).Visit(null, parentNode, true, modSet);
            }
        }
Beispiel #4
0
        /// <summary>
        /// Visits an event or machine declaration.
        /// </summary>
        /// <param name="parentNode">Node</param>
        /// <param name="tokenRange">The range of accumulated tokens</param>
        private void VisitEventOrMachineDeclaration(NamespaceDeclaration parentNode, TokenRange tokenRange)
        {
            ModifierSet modSet = ModifierSet.CreateDefault();

            while (!this.TokenStream.Done &&
                   this.TokenStream.Peek().Type != TokenType.EventDecl &&
                   this.TokenStream.Peek().Type != TokenType.MachineDecl &&
                   this.TokenStream.Peek().Type != TokenType.MonitorDecl)
            {
                new ModifierVisitor(this.TokenStream).Visit(modSet);

                this.TokenStream.Index++;
                this.TokenStream.SkipWhiteSpaceAndCommentTokens();
            }

            if (this.TokenStream.Done ||
                (this.TokenStream.Peek().Type != TokenType.EventDecl &&
                 this.TokenStream.Peek().Type != TokenType.MachineDecl &&
                 this.TokenStream.Peek().Type != TokenType.MonitorDecl))
            {
                throw new ParsingException("Expected event, machine or monitor declaration.", this.TokenStream.Peek(),
                                           TokenType.EventDecl,
                                           TokenType.MachineDecl,
                                           TokenType.MonitorDecl);
            }

            if (this.TokenStream.Peek().Type == TokenType.EventDecl)
            {
                new EventDeclarationVisitor(this.TokenStream).Visit(parentNode, null, modSet);
            }
            else if (this.TokenStream.Peek().Type == TokenType.MachineDecl)
            {
                new MachineDeclarationVisitor(this.TokenStream).Visit(parentNode, false, modSet, tokenRange.Start());
            }
            else if (this.TokenStream.Peek().Type == TokenType.MonitorDecl)
            {
                new MachineDeclarationVisitor(this.TokenStream).Visit(parentNode, true, modSet, tokenRange.Start());
            }
        }
Beispiel #5
0
        /// <summary>
        /// Visits a group level declaration.
        /// </summary>
        /// <param name="parentNode">Node</param>
        private void VisitGroupLevelDeclaration(StateGroupDeclaration parentNode)
        {
            ModifierSet modSet = ModifierSet.CreateDefault();

            while (!base.TokenStream.Done &&
                   base.TokenStream.Peek().Type != TokenType.StateDecl &&
                   base.TokenStream.Peek().Type != TokenType.StateGroupDecl &&
                   base.TokenStream.Peek().Type != TokenType.MachineDecl)
            {
                new ModifierVisitor(base.TokenStream).Visit(modSet);

                base.TokenStream.Index++;
                base.TokenStream.SkipWhiteSpaceAndCommentTokens();
            }

            if (base.TokenStream.Done ||
                (base.TokenStream.Peek().Type != TokenType.StateDecl &&
                 base.TokenStream.Peek().Type != TokenType.StateGroupDecl))
            {
                throw new ParsingException("Expected state or group declaration.",
                                           new List <TokenType>
                {
                    TokenType.StateDecl,
                    TokenType.StateGroupDecl
                });
            }

            if (base.TokenStream.Peek().Type == TokenType.StateDecl)
            {
                new StateDeclarationVisitor(base.TokenStream).Visit(parentNode.Machine, parentNode, modSet);
            }
            else if (base.TokenStream.Peek().Type == TokenType.StateGroupDecl)
            {
                new StateGroupDeclarationVisitor(base.TokenStream).Visit(parentNode.Machine, parentNode, modSet);
            }
        }
        /// <summary>
        /// Visits a machine level declaration.
        /// </summary>
        private void VisitMachineLevelDeclaration(MachineDeclaration parentNode, TokenRange tokenRange)
        {
            var modSet = ModifierSet.CreateDefault();

            while (!this.TokenStream.Done &&
                   this.TokenStream.Peek().Type != TokenType.EventDecl &&
                   this.TokenStream.Peek().Type != TokenType.StateDecl &&
                   this.TokenStream.Peek().Type != TokenType.StateGroupDecl &&
                   this.TokenStream.Peek().Type != TokenType.MachineDecl &&
                   this.TokenStream.Peek().Type != TokenType.Void &&
                   this.TokenStream.Peek().Type != TokenType.Object &&
                   this.TokenStream.Peek().Type != TokenType.String &&
                   this.TokenStream.Peek().Type != TokenType.Sbyte &&
                   this.TokenStream.Peek().Type != TokenType.Byte &&
                   this.TokenStream.Peek().Type != TokenType.Short &&
                   this.TokenStream.Peek().Type != TokenType.Ushort &&
                   this.TokenStream.Peek().Type != TokenType.Int &&
                   this.TokenStream.Peek().Type != TokenType.Uint &&
                   this.TokenStream.Peek().Type != TokenType.Long &&
                   this.TokenStream.Peek().Type != TokenType.Ulong &&
                   this.TokenStream.Peek().Type != TokenType.Char &&
                   this.TokenStream.Peek().Type != TokenType.Bool &&
                   this.TokenStream.Peek().Type != TokenType.Decimal &&
                   this.TokenStream.Peek().Type != TokenType.Float &&
                   this.TokenStream.Peek().Type != TokenType.Double &&
                   this.TokenStream.Peek().Type != TokenType.Identifier)
            {
                new ModifierVisitor(this.TokenStream).Visit(modSet);

                this.TokenStream.Index++;
                this.TokenStream.SkipWhiteSpaceAndCommentTokens();
            }

            if (this.TokenStream.Done ||
                (this.TokenStream.Peek().Type != TokenType.EventDecl &&
                 this.TokenStream.Peek().Type != TokenType.StateDecl &&
                 this.TokenStream.Peek().Type != TokenType.StateGroupDecl &&
                 this.TokenStream.Peek().Type != TokenType.MachineDecl &&
                 this.TokenStream.Peek().Type != TokenType.Void &&
                 this.TokenStream.Peek().Type != TokenType.Object &&
                 this.TokenStream.Peek().Type != TokenType.String &&
                 this.TokenStream.Peek().Type != TokenType.Sbyte &&
                 this.TokenStream.Peek().Type != TokenType.Byte &&
                 this.TokenStream.Peek().Type != TokenType.Short &&
                 this.TokenStream.Peek().Type != TokenType.Ushort &&
                 this.TokenStream.Peek().Type != TokenType.Int &&
                 this.TokenStream.Peek().Type != TokenType.Uint &&
                 this.TokenStream.Peek().Type != TokenType.Long &&
                 this.TokenStream.Peek().Type != TokenType.Ulong &&
                 this.TokenStream.Peek().Type != TokenType.Char &&
                 this.TokenStream.Peek().Type != TokenType.Bool &&
                 this.TokenStream.Peek().Type != TokenType.Decimal &&
                 this.TokenStream.Peek().Type != TokenType.Float &&
                 this.TokenStream.Peek().Type != TokenType.Double &&
                 this.TokenStream.Peek().Type != TokenType.Identifier))
            {
                throw new ParsingException("Expected event, state, group or method declaration.", this.TokenStream.Peek(),
                                           TokenType.EventDecl,
                                           TokenType.StateDecl,
                                           TokenType.StateGroupDecl,
                                           TokenType.MachineDecl,
                                           TokenType.Void,
                                           TokenType.Object,
                                           TokenType.String,
                                           TokenType.Sbyte,
                                           TokenType.Byte,
                                           TokenType.Short,
                                           TokenType.Ushort,
                                           TokenType.Int,
                                           TokenType.Uint,
                                           TokenType.Long,
                                           TokenType.Ulong,
                                           TokenType.Char,
                                           TokenType.Bool,
                                           TokenType.Decimal,
                                           TokenType.Float,
                                           TokenType.Double,
                                           TokenType.Identifier);
            }

            if (this.TokenStream.Peek().Type == TokenType.EventDecl)
            {
                new EventDeclarationVisitor(this.TokenStream).Visit(parentNode.Namespace, parentNode, modSet);
            }
            else if (this.TokenStream.Peek().Type == TokenType.StateDecl)
            {
                new StateDeclarationVisitor(this.TokenStream).Visit(parentNode, null, modSet, tokenRange.Start());
            }
            else if (this.TokenStream.Peek().Type == TokenType.StateGroupDecl)
            {
                new StateGroupDeclarationVisitor(this.TokenStream).Visit(parentNode, null, modSet, tokenRange.Start());
            }
            else
            {
                new MachineMemberDeclarationVisitor(this.TokenStream).Visit(parentNode, modSet);
            }
        }
        private void VisitBaseEventDeclaration(EventDeclaration node, EventDeclarations declarations)
        {
            if (!base.TokenStream.Done && base.TokenStream.Peek().Type == TokenType.Colon)
            {
                base.TokenStream.Index++;
                base.TokenStream.SkipWhiteSpaceAndCommentTokens();
                if (base.TokenStream.Done || base.TokenStream.Peek().Type != TokenType.Identifier)
                {
                    throw new ParsingException("Expected event identifier.",
                                               new List <TokenType> {
                        TokenType.Identifier
                    });
                }

                // We only use referencingNode to verify the name exists and the generic type matches.
                var referencingNode = new EventDeclaration(base.TokenStream.Program, null, ModifierSet.CreateDefault())
                {
                    Identifier = NameVisitor.VisitSimpleQualifiedName(base.TokenStream, TokenType.EventIdentifier)
                };

                if (!declarations.Find(referencingNode.Identifier.Text, out var baseEventDecl))
                {
                    throw new ParsingException($"Could not find definition or extern declaration of base event {referencingNode.Identifier.Text}.",
                                               new List <TokenType> {
                    });
                }

                if (!base.TokenStream.Done)
                {
                    VisitGenericType(referencingNode);
                    if (referencingNode.GenericType.Count != baseEventDecl.GenericType.Count)
                    {
                        throw new ParsingException($"Mismatch in number of generic type arguments for base event {referencingNode.Identifier.Text}.",
                                                   new List <TokenType> {
                        });
                    }
                }
                node.BaseClassDecl = baseEventDecl;
            }
        }