/* HeuristicLab * Copyright (C) 2002-2013 Heuristic and Evolutionary Algorithms Laboratory (HEAL) * * This file is part of HeuristicLab. * * HeuristicLab is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * HeuristicLab is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with HeuristicLab. If not, see . */ // Coco/R grammar for the GPDL compiler $namespace=HeuristicLab.Problems.GPDL using System.Text; using System.Collections.Generic; using System.Linq; using IEnumerableConstraintNode = System.Collections.Generic.IEnumerable; COMPILER GPDef public GPDefNode AbstractSyntaxTree { get; private set; } CHARACTERS letter = 'A'..'Z' + 'a'..'z'. digit = '0'..'9'. TOKENS ident = letter {letter | digit} . COMMENTS FROM "/*" TO "*/" NESTED COMMENTS FROM "//" TO "\r" IGNORE '\t' + '\r' + '\n' PRODUCTIONS SourceCode = (. src = ""; .) "<<" (. int beg = la.pos; .) {ANY} (. int end = la.pos; .) ">>" (. if(end>beg) src = scanner.buffer.GetString(beg, end); .) . GPDef = (. RuleNode ruleNode = null; GPDefNode gpDef = new GPDefNode(); NonTerminalNode ntNode = null; FitnessFunctionNode fitnessFunNode = null; TerminalNode tNode = null; string src = ""; .) "PROBLEM" ident (. gpDef.Name = t.val; .) ["CODE" SourceCode (. gpDef.ClassCodeNode = new CodeNode{SrcCode = src}; .) ] ["INIT" SourceCode (. gpDef.InitCodeNode = new CodeNode{SrcCode = src}; .) ] "NONTERMINALS" { NonterminalDecl (. if(gpDef.IsSymbolDefined(ntNode)) { SemErr("Duplicate non-terminal symbol: " + ntNode.Ident); } else { gpDef.NonTerminals.Add(ntNode); } .) } (. if(!gpDef.NonTerminals.Any()) SemErr("No non-terminal symbols defined."); .) "TERMINALS" { TerminalDecl (. if(gpDef.IsSymbolDefined(tNode)) { SemErr("Duplicate terminal symbol: " + tNode.Ident); } else { gpDef.Terminals.Add(tNode); } .) } (. if(!gpDef.Terminals.Any()) SemErr("No terminal symbols defined."); .) "RULES" { RuleDef (. if(!gpDef.IsNonTerminalDefined(ruleNode.NtSymbol)) { SemErr("Non-terminal symbol " + ruleNode.NtSymbol + " is not defined in the NONTERMINALS section."); } else if(gpDef.IsRuleDefined(ruleNode)) { SemErr("Duplicate rule definition for non-terminal symbol " + ruleNode.NtSymbol); } else { gpDef.Rules.Add(ruleNode); } .) } (. var undefinedNT = gpDef.UndefinedNonTerminals(); if(!string.IsNullOrEmpty(undefinedNT)) { SemErr("Rules missing in the RULES section for: " + undefinedNT); } .) (. fitnessFunNode = new FitnessFunctionNode(); gpDef.FitnessFunctionNode = fitnessFunNode; .) ("MAXIMIZE" (. fitnessFunNode.Maximization = true; .) | "MINIMIZE" (. fitnessFunNode.Maximization = false; .) ) SourceCode (. fitnessFunNode.SrcCode = src; .) (. if(errors.count > 0) throw new FatalError("Syntactic or semantic errors found."); .) "END" ident (. AbstractSyntaxTree = gpDef; .) '.' . /******************************************************/ SemAction = (. RuleActionNode myAction = null; action = null; string src = ""; .) "SEM" SourceCode (. myAction = new RuleActionNode(); myAction.SrcCode = src; action = myAction; .) . /******************************************************/ NonterminalDecl = (. string identStr = ""; ntNode = null; string src = ""; .) ident (. identStr = t.val; .) [ SourceCode ] (. var myNtNode = new NonTerminalNode(); ntNode = myNtNode; myNtNode.Ident = identStr; myNtNode.FormalParameters = src; .) '.' . /******************************************************/ TerminalDecl = (. string identStr = ""; tNode = null; TerminalNode myTNode = null; IEnumerableConstraintNode constraints = new List(); string src = ""; .) ident (. identStr = t.val; .) [ SourceCode ] (. myTNode = new TerminalNode(); tNode = myTNode; myTNode.Ident = identStr; myTNode.FormalParameters = src; myTNode.FieldDefinitions = Util.ExtractParameters(src); .) [ "CONSTRAINTS" ConstraintDef ] (. myTNode.Constraints = constraints; .) '.' . /******************************************************/ ConstraintDef = (. List constraintsList = new List(); ConstraintNode n = null; constraints = null; .) { ConstraintRule (. constraintsList.Add(n); .) } (. constraints = constraintsList; .) . /******************************************************/ ConstraintRule = (. constraint = null; .) ident (. constraint = new ConstraintNode(t.val); .) "IN" SetDefinition . /******************************************************/ SetDefinition = (. string src = ""; .) ("SET" (. constraint.Type = ConstraintNodeType.Set; .) SourceCode (. constraint.SetExpression = src; .) | "RANGE" (. constraint.Type = ConstraintNodeType.Range; .) SourceCode (. constraint.RangeMinExpression = src; .) ".." SourceCode (. constraint.RangeMaxExpression = src; .) ) . /******************************************************/ RuleDef = (. AlternativesNode alternatives = null; string identStr = null; RuleNode myRule = null; rule = null; string src = ""; .) ident (. identStr = t.val; .) [ SourceCode ] '=' (. myRule = new RuleNode(); rule = myRule; myRule.NtSymbol = identStr; .) ["LOCAL" SourceCode (. myRule.LocalCode = src; .) ] SynExpr '.' (. myRule.Alternatives = alternatives; .) . /******************************************************/ SynExpr = (. alt = new AlternativesNode(); SequenceNode seq = null; .) SynTerm (. alt.Add(seq); .) { '|' SynTerm (. alt.Add(seq); .) } . /******************************************************/ SynTerm = (. seq = new SequenceNode(); RuleExprNode expr = null; .) SynFact (. seq.Add(expr); .) { SynFact (. seq.Add(expr); .) } . /******************************************************/ SynFact = (. string identStr = ""; RuleActionNode action = null; expr = null; string src = ""; .) (ident (. identStr = t.val; .) [ SourceCode ] (. var callNode = new CallSymbolNode{Ident = identStr}; callNode.ActualParameter = src; expr = callNode; .) // not implemented | "EPS" // not implemented | '(' SynExpr ')' // not implemented | '[' SynExpr ']' // not implemented | '{' SynExpr '}' | SemAction (. expr = action; .) ) . END GPDef.