Exemple #1
0
		public void CreateSpecialProduction(NonTerminal root)
		{
			this.rootProduction = new Production(this.LookupNonTerminal("$accept"));
			this.AddProduction(this.rootProduction);
			this.rootProduction.rhs.Add(root);
			this.rootProduction.rhs.Add(this.LookupTerminal(GrammarToken.Symbol, "EOF"));
		}
Exemple #2
0
		public SemanticAction(Production production, int startLine, int pos, string commands)
		{
			this.production = production;
			this.pos = pos;
			this.startLine = startLine;
			this.commands = commands;
		}
Exemple #3
0
		private void AddNonKernal(Production production)
		{
			ProductionItem item = new ProductionItem(production, 0);
			if (!this.all_items.Contains(item))
			{
				this.all_items.Add(item);
				this.AddClosure(item);
			}
		}
Exemple #4
0
        public static void Calculate(Production p)
        {
            // Precedence of a production is that of its rightmost terminal
            // unless explicitly labelled with %prec

            if (p.prec == null)
                for (int i = p.rhs.Count - 1; i >= 0; i--)
                    if (p.rhs[i] is Terminal)
                    {
                        p.prec = ((Terminal)p.rhs[i]).prec;
                        break;
                    }
        }
Exemple #5
0
		public static void Calculate(Production p)
		{
			if (p.prec == null)
			{
				for (int i = p.rhs.Count - 1; i >= 0; i--)
				{
					if (p.rhs[i] is Terminal)
					{
						p.prec = ((Terminal)p.rhs[i]).prec;
						return;
					}
				}
			}
		}
Exemple #6
0
		public State(Production production)
		{
			this.num = State.TotalStates++;
			this.AddKernal(production, 0);
		}
Exemple #7
0
		public ProductionItem(Production production, int pos)
		{
			this.production = production;
			this.pos = pos;
		}
Exemple #8
0
 public void CreateSpecialProduction(NonTerminal root)
 {
     rootProduction = new Production(LookupNonTerminal("$accept"));
     AddProduction(rootProduction);
     rootProduction.rhs.Add(root);
     rootProduction.rhs.Add(LookupTerminal(GrammarToken.Symbol, "END_OF_FILE"));
 }
 private void GenerateRule(Production production)
 {
     Console.Write("    rules[{0}]=new Rule({1}, new int[]{{", production.num, production.lhs.num);
     bool first = true;
     foreach (Symbol sym in production.rhs)
     {
         if (!first)
             Console.Write(",");
         else
             first = false;
         Console.Write("{0}", sym.num);
     }
     Console.WriteLine("});");
 }
Exemple #10
0
 private void AddKernal(Production production, int pos)
 {
     ProductionItem item = new ProductionItem(production, pos);
     kernal_items.Add(item);
     all_items.Add(item);
 }
Exemple #11
0
		public void AddProduction(Production production)
		{
			this.productions.Add(production);
			production.num = this.productions.Count;
		}
Exemple #12
0
 public ProductionItem(Production production, int pos)
 {
     this.production = production;
     this.pos        = pos;
 }
Exemple #13
0
 public State(Production production)
 {
     num = TotalStates++;
     AddKernal(production, 0);
 }
Exemple #14
0
		private State PathTo(State q, Production prod, int prefix)
		{
			for (int i = 0; i < prefix; i++)
			{
				Symbol key = prod.rhs[i];
				if (!q.Goto.ContainsKey(key))
				{
					return null;
				}
				q = q.Goto[key];
			}
			return q;
		}
Exemple #15
0
 public void AddProduction(Production production)
 {
     productions.Add(production);
     production.num = productions.Count;
 }
Exemple #16
0
		private void GenerateRule(Production production)
		{
            this.output.Write("    new Rule(" + production.lhs.num + ", new int[]{");
			bool flag = true;
			foreach (Symbol current in production.rhs)
			{
				if (!flag)
				{
					this.output.Write(",");
				}
				else
				{
					flag = false;
				}
				this.output.Write("{0}", current.num);
			}
			this.output.WriteLine("}),");
		}
        private State PathTo(State q, Production prod, int prefix)
        {
            // q -> prod.rhs[0] ... prod.rhs[prefix] -> ???

            for (int i = 0; i < prefix; i++)
            {
                Symbol s = prod.rhs[i];
                if (q.Goto.ContainsKey(s))
                    q = q.Goto[s];
                else
                    return null;
            }

            return q;
        }
Exemple #18
0
 public State(Production production)
 {
     num = TotalStates++;
     AddKernal(production, 0);
 }
Exemple #19
0
        private void ParseRhs(NonTerminal lhs)
        {
            Production production = new Production(lhs);
            int pos = 0;

            while (token == GrammarToken.Symbol || token == GrammarToken.Literal ||
                   token == GrammarToken.Action || token == GrammarToken.Prec)
            {
                switch (token)
                {
                    case GrammarToken.Literal:
                    {
                        production.rhs.Add(grammar.LookupTerminal(token, scanner.yylval));
                        Advance();
                        pos++;
                        break;
                    }
                    case GrammarToken.Symbol:
                    {
                        if (grammar.terminals.ContainsKey(scanner.yylval))
                            production.rhs.Add(grammar.terminals[scanner.yylval]);
                        else
                            production.rhs.Add(grammar.LookupNonTerminal(scanner.yylval));
                        Advance();
                        pos++;
                        break;
                    }
                    case GrammarToken.Prec:
                    {
                        Advance();
                        if (token == GrammarToken.Symbol)
                        {
                            production.prec = grammar.LookupTerminal(token, scanner.yylval).prec;
                            Advance();
                        }
                        else
                            scanner.ReportError("Expected symbol after %prec");
                        break;
                    }
                    case GrammarToken.Action:
                    {
                        SemanticAction semanticAction = new SemanticAction(production, pos, scanner.yylval);
                        Advance();

                        if (token == GrammarToken.Divider || token == GrammarToken.SemiColon || token == GrammarToken.Prec) // reduce action
                            production.semanticAction = semanticAction;
                        else
                        {
                            NonTerminal node = grammar.LookupNonTerminal("@" + (++grammar.NumActions).ToString());
                            Production nullProduction = new Production(node);
                            nullProduction.semanticAction = semanticAction;
                            grammar.AddProduction(nullProduction);
                            production.rhs.Add(node);
                        }
                        pos++;
                        break;
                    }
                }
            }

            grammar.AddProduction(production);

            Precedence.Calculate(production);
        }
Exemple #20
0
		private void ParseRhs(NonTerminal lhs)
		{
			Production production = new Production(lhs);
			int num = 0;
			while (this.token == GrammarToken.Symbol || this.token == GrammarToken.Literal || this.token == GrammarToken.Action || this.token == GrammarToken.Prec)
			{
				GrammarToken grammarToken = this.token;
				switch (grammarToken)
				{
				case GrammarToken.Symbol:
					if (this.grammar.terminals.ContainsKey(this.scanner.yylval))
					{
						production.rhs.Add(this.grammar.terminals[this.scanner.yylval]);
					}
					else
					{
						production.rhs.Add(this.grammar.LookupNonTerminal(this.scanner.yylval));
					}
					this.Advance();
					num++;
					break;
				case GrammarToken.Literal:
					production.rhs.Add(this.grammar.LookupTerminal(this.token, this.scanner.yylval));
					this.Advance();
					num++;
					break;
				case GrammarToken.Action:
				{
					SemanticAction semanticAction = new SemanticAction(production, this.tokenStartLine, num, this.scanner.yylval);
					this.Advance();
					if (this.token == GrammarToken.Divider || this.token == GrammarToken.SemiColon || this.token == GrammarToken.Prec)
					{
						production.semanticAction = semanticAction;
					}
					else
					{
						Grammar arg_1BA_0 = this.grammar;
						string arg_1B5_0 = "@";
						int num2 = ++this.grammar.NumActions;
						NonTerminal nonTerminal = arg_1BA_0.LookupNonTerminal(arg_1B5_0 + num2.ToString());
						Production production2 = new Production(nonTerminal);
						production2.semanticAction = semanticAction;
						this.grammar.AddProduction(production2);
						production.rhs.Add(nonTerminal);
					}
					num++;
					break;
				}
				default:
					if (grammarToken == GrammarToken.Prec)
					{
						this.Advance();
						if (this.token == GrammarToken.Symbol)
						{
							production.prec = this.grammar.LookupTerminal(this.token, this.scanner.yylval).prec;
							this.Advance();
						}
						else
						{
							this.scanner.ReportError("Expected symbol after %prec", new object[0]);
						}
					}
					break;
				}
			}
			this.grammar.AddProduction(production);
			Precedence.Calculate(production);
		}
Exemple #21
0
        private void GenerateActionMethod(List <Production> productions)
        {
            // TODO: parameterize; it seems that 0 is optimal though
            const int GroupSizeLog = 0;

            int groupSize  = 1 << GroupSizeLog;
            int mask       = groupSize - 1;
            int groupCount = (productions.Count >> GroupSizeLog) + ((productions.Count & mask) != 0 ? 1 : 0);

            Console.WriteLine("  protected override void DoAction(int action)");
            Console.WriteLine("  {");

            List <int> nonEmptyProductionCounts = new List <int>();

            for (int g = 0; g < groupCount; g++)
            {
                int nonEmptyCount = 0;
                for (int i = 0; i < groupSize; i++)
                {
                    int index = (g << GroupSizeLog) + i;
                    if (index >= productions.Count)
                    {
                        break;
                    }
                    if (productions[index].semanticAction != null)
                    {
                        nonEmptyCount++;
                    }
                }
                nonEmptyProductionCounts.Add(nonEmptyCount);
            }

            Debug.Assert(nonEmptyProductionCounts.Count == groupCount);

            if (groupCount > 1)
            {
                if (groupSize > 1)
                {
                    Console.WriteLine("    int mod = action & 0x{0:X};", mask);
                    Console.WriteLine("    switch (action  >> {0})", GroupSizeLog);
                }
                else
                {
                    Console.WriteLine("    switch (action)", GroupSizeLog);
                }

                Console.WriteLine("    {");

                for (int g = 0; g < groupCount; g++)
                {
                    if (nonEmptyProductionCounts[g] > 0)
                    {
                        Console.WriteLine("      case {0}: _{0}({1}); return;", g, groupSize > 1 ? "mod" : "");
                    }
                }

                Console.WriteLine("    }");
            }
            else
            {
                Console.WriteLine("    _0(action);");
            }

            Console.WriteLine("  }");
            Console.WriteLine();

            for (int g = 0; g < groupCount; g++)
            {
                if (nonEmptyProductionCounts[g] > 0)
                {
                    Console.WriteLine("  private void _{0}({1})", g, groupSize > 1 ? "int mod" : "");
                    Console.WriteLine("  {");

                    if (groupSize > 1)
                    {
                        Console.WriteLine("    switch (mod)");
                        Console.WriteLine("    {");
                    }

                    for (int i = 0; i < groupSize; i++)
                    {
                        int index = (g << GroupSizeLog) + i;
                        if (index >= productions.Count)
                        {
                            break;
                        }

                        Production production = productions[index];
                        Debug.Assert(index == production.num - 1);

                        if (production.semanticAction != null)
                        {
                            if (groupSize > 1)
                            {
                                Console.WriteLine("      case {0}:", i);
                            }

                            Console.WriteLine("      // " + production.ToString());

                            production.semanticAction.GenerateCode(this);

                            if (groupSize > 1)
                            {
                                Console.WriteLine("        return;");
                            }
                        }
                    }

                    if (groupSize > 1)
                    {
                        Console.WriteLine("      default: return;");
                        Console.WriteLine("    }");
                    }

                    Console.WriteLine("  }");
                    Console.WriteLine();
                }
            }
        }