JustPaste.it
User avatar
@anonymous · Feb 17, 2021

%tokentype Token

// Add '%using' here
%using QUT;
%using NETSchemeCore.Utils;
%using System.Linq;
%using System.Linq.Expressions;
%using System.Runtime.CompilerServices;
%using Microsoft.SolverFoundation.Common;
%using System.Diagnostics;

 

%namespace NETSchemeCore

%visibility internal
%partial
%parsertype Parser

%{
    // Insert user code here if needed


    private Engine _engine;
    private Context _topLevel;
    private Context _currentContext;
    private Stack<NSCParserState> _state;
    private NSSTTreeNode _syntaxTree;
    public NSCDatum last_Expr = null;
    private NSSProgramNode _program;
    private bool _debug;
%}

// Define the name of the location type (default = LexLocation).
// U must provide a class with that name.
//%YYLTYPE LexSpan

// Define the name of the semantic type (default = int).
// U must provide a class with that name.
%YYSTYPE object

// Define the semantic value-type declaration (incompatible with '%YYSTYPE').
//%union 
//{
//}

// Start of token definitions
%token IDENTIFIER
%token TRUE
%token FALSE
%token NUMBER
%token CHARACTER
%token STRING
%token ID_QUOTE
%token IF
%token OPEN_PARENTHESES        "(" 
%token CLOSE_PARENTHESES    ")"
%token OPEN_BRACKETS        "["
%token CLOSE_BRACKETS        "]"
%token QUOTEMARK            "`"
%token SINGLE_QUOTE            "'"
%token COMMA                ","
%token COMMA_AT                ",@"
%token HASH_QUOTEMARK        "#`"
%token HASH_SINGLE_QUOTE    "#'"
%token HASH_COMMA            "#,"
%token HASH_COMMA_AT        "#,@"
%token OPEN_VECTOR            "#("
%token OPEN_BYTE_VECTOR        "#vu8("
%token PERIOD                "."
%token IMPLICATIVE            "=>"
%token IMPORT                "import"
%token DEFINE                "define"
%token QUOTE                "quote"
%token LAMBDA                "lambda"
%token SET                    "set!"
%token CONDITIONAL            "cond"
%token ELSE                    "else"
%token CASE                    "case"
%token AND                    "and"
%token OR                    "or"
%token BEGIN                "begin"
%token LET                  "let"
%token LETREC                  "letrec"
%token LETSTAR                 "let*"
%token LETRECSTAR            "letrec*"

%start Top_level

%%  

// Start of rules definitions


//<Top level> -> (<import form> | <Top-level body>)*
Top_level
    :
    | importform
    | toplevel_body
    ;

// <import form> -> (import <import specs>)
importform
    : "import"
/*    : "import" // import_spec
*/
    ;

//Ler o manual
//import_spec
//    :
//    ;

// <Top-level body> -> <definition> | <expression>
toplevel_body
    : definition    {
                        try
                        {
                           _engine.AddExpression((Expression)$1);
                           _engine.compile(_debug);
                           var res = _engine.run();
                           Console.WriteLine(res.ToString());
                           Engine.showHierarchy(res);
                              _engine.clear();

 

/*                            _program.addNode((NSSTTreeNode)$1);
                            NSCDatum result = CCSS.eval(_program, _topLevel, 0);    
                            //NSCDatum result = _program.Eval(_topLevel);                        
                            Console.WriteLine(result.ToString());*/
                        } catch(Exception ex)
                        {
                             while (ex != null) {
                                Trace.TraceError(ex.ToString());
                                ex = ex.InnerException;
                             }
                            //Console.WriteLine("Error:" + e.Message + " " + e.TargetSite.Name);
                            //Console.WriteLine(e.StackTrace);
                            last_Expr = null;
                        }
                    }
    | "(" BEGIN body ")"    {
                                _program.addNode(new NSSBegin1Node(((List<NSSTTreeNode>)$3)));
                                //_program.Eval(_topLevel);
                                CCSS.eval(_program, _topLevel, 0);
                            }
    | expression    {   
                        try
                        {
                           _engine.AddExpression((Expression)$1);
                           _engine.compile(_debug);
                           var res = _engine.run();
                           Console.WriteLine(res.ToString());
                           Engine.showHierarchy(res);
                              _engine.clear();
                           /*
                            _program.addNode((NSSTTreeNode)$1);    
                            //NSCDatum result = _program.Eval(_topLevel);        
                            NSCDatum result = CCSS.eval(_program, _topLevel, 0);
                            Console.WriteLine(result.ToString());*/
                        } catch(Exception ex)
                        {
                             _engine.clear();
                             while (ex != null) {
                                Trace.TraceError(ex.ToString());
                                ex = ex.InnerException;
                             }
                            //Console.WriteLine("Error:" + e.Message + " " + e.TargetSite.Name);
                            //Console.WriteLine(e.StackTrace);
                            last_Expr = null;
                        }
                    }
    | IDENTIFIER    {
                        if (((String)$1).ToUpper() == "QUIT" ) Environment.Exit(0);
                        if (((String)$1).ToUpper() == "HELP" ) 
                        {
                            Console.WriteLine("To more information type (HELP [COMMAND] )");
                            Console.WriteLine("syntactic keywords:");
                            Console.WriteLine("access                  define-syntax           macro");
                            Console.WriteLine("and                     delay                   make-environment");
                            Console.WriteLine("begin                   do                      named-lambda");
                            Console.WriteLine("bkpt                    fluid-let               or");
                            Console.WriteLine("case                    if                      quasiquote");
                            Console.WriteLine("cond                    in-package              quote");
                            Console.WriteLine("cons-stream             lambda                  scode-quote");
                            Console.WriteLine("declare                 let                     sequence");
                            Console.WriteLine("default-object?         let*                    set!");
                            Console.WriteLine("define                  let-syntax              the-environment");
                            Console.WriteLine("define-integrable       letrec                  unassigned?");
                            Console.WriteLine("define-macro            letrec*                 using-syntax");
                            Console.WriteLine("define-structure        local-declare");
                        }
                        $$ = Engine.get((String)$1);
                    }

    ; 

body
    : expressions    {
                        $$ = new Body(new List<Expression>(), (List<Expression>)$1);
                    }
    | definitions expressions    {
                                    $$ = new Body((List<Expression>)$1, (List<Expression>)$2);
                                }
    ;

cond_clause
    : expression expressions    {
                                    if ($1 is NSSErrorNode) $$ = $1;
                                    else if ($2 is NSSErrorNode) $$ = $2;
                                         else 
                                         {
                                            NSSCondClause result = new NSSCondClause()
                                            {
                                                condition = (NSSTTreeNode)$1,
                                                expresions =(List<NSSTTreeNode>)$2
                                            };
                                            $$ = result;
                                         }
                                    ((NSSTTreeNode)$$).quotation = "(" + ((NSSTTreeNode)$1).quotation + " " + NSSQuotationNode.quoteList( (List<NSSTTreeNode>)$2 ) + ")";
                                }
    | expression "=>" expression    {
                                        if ($1 is NSSErrorNode) $$ = $1;
                                        else if ($3 is NSSErrorNode) $$ = $3;
                                             else
                                             {
                                                   NSSCondClause result = new NSSCondClause()
                                                 {
                                                     condition = (NSSTTreeNode)$1,
                                                     function = (NSSLambdaNode)$3
                                                 };
                                                 $$ = result;
                                             }
                                        ((NSSTTreeNode)$$).quotation = "(" + ((NSSTTreeNode)$1).quotation + "=>" + ((NSSLambdaNode)$3).quotation + ")";                                    
                                    }
    ;

cond_clauses
    : "(" cond_clause ")"    {
                                if ($2 is NSSErrorNode)
                                { 
                                    $$ = $2;
                                    ((NSSTTreeNode)$$).quotation = "(" + ((NSSTTreeNode)$2).quotation + ")";
                                } else
                                {
                                    if (($$ == null) || !($$ is List<NSSCondClause>)) $$ = new List<NSSCondClause>();
                                    ((List<NSSCondClause>)$$).Add((NSSCondClause)$2);
                                }
                            }
    | cond_clauses "(" cond_clause ")"    {
                                            if ($1 is NSSErrorNode) $$ = $1;
                                            else if ($3 is NSSErrorNode) $$ = $3;
                                                 else
                                                 {
                                                      if (($$ == null) || !($$ is List<NSSCondClause>)) $$ = $1;
                                                     ((List<NSSCondClause>)$$).Add((NSSCondClause)$3);
                                                 }
                                            if ($$ is NSSErrorNode) ((NSSTTreeNode)$$).quotation = (($1 is NSSErrorNode)? ((NSSTTreeNode)$1).quotation : NSSQuotationNode.quoteList((List<NSSCondClause>)$1)) + (($3 is NSSErrorNode)? ((NSSTTreeNode)$3).quotation : "(" + ((NSSTTreeNode)$3).quotation + ")");
                                        }
    ;

case_clause
    : "(" list expressions ")"    {
                                    NSSCaseClause result = new NSSCaseClause()
                                    {
                                        conditions = (NSCPair)$2,
                                        expresions = (List<NSSTTreeNode>)$3,
                                        quotation = "(" + ((NSCDatum)$2).quotedText + NSSQuotationNode.quoteList((List<NSSTTreeNode>)$3) + ")"
                                    };
                                    $$ = result;
                                }
    ;

case_clauses
    : case_clause    {
                        if (($$ == null) || !($$ is List<NSSCaseClause>)) $$ = new List<NSSCaseClause>();
                        ((List<NSSCaseClause>)$$).Add((NSSCaseClause)$1);
                    }
    | case_clauses case_clause    {
                                    if (($$ == null) || !($$ is List<NSSCaseClause>)) $$ = $1;
                                    ((List<NSSCaseClause>)$$).Add((NSSCaseClause)$2);
                                }
    ;

else_clause
    : "(" ELSE expressions ")"    {
                                    $$ = $3;
                                    if ($3 is NSSErrorNode) ((NSSTTreeNode)$$).quotation = "(" + (String)$2 + " " + ((NSSTTreeNode)$3).quotation + ")";
                                }
    ;

def_formals
    : identifiers            {
                                NSSFormals result = new NSSFormals();
                                result.parameters = (List<String>)$1;
                                result.type = 0;
                                $$ = result;
                            }
    | identifiers "." IDENTIFIER            {
                                                NSSFormals result = new NSSFormals();
                                                result.parameters = (List<String>)$1;
                                                result.parameters.Add((String)$3);
                                                result.type = 2;
                                                $$ = result;
                                            }
    ;


definition
    : "(" DEFINE "(" IDENTIFIER def_formals ")" body ")"    {
                                                                $$ = Engine.define((String)$4, Engine.lambda((Body)$7,(NSSFormals)$5, _engine.environment._location));
                                                        }
    | "(" DEFINE IDENTIFIER expression ")"    {
                                                $$ = Engine.define((String)$3,(Expression)$4);
                                            }
    | "(" DEFINE IDENTIFIER ")"    {
                                    $$ = Engine.define((String)$3); 
                                }
    | "(" DEFINE "(" IDENTIFIER "." IDENTIFIER ")" body ")"
    ;

definitions
    : definition    {
                        if (($$ == null) || !($$ is List<NSSTTreeNode>)) $$ = new List<NSSTTreeNode>();
                        ((List<NSSTTreeNode>)$$).Add((NSSTTreeNode)$1);
                    }
    | definitions definition    {
                                    if (($$ == null) || !($$ is List<NSSTTreeNode>)) $$ = $1;
                                    ((List<NSSTTreeNode>)$$).Add((NSSTTreeNode)$2);
                                }
    ;

formals
    : "(" identifiers ")"    {
                                NSSFormals result = new NSSFormals();
                                result.parameters = (List<String>)$2;
                                result.type = 0;
                                $$ = result;
                            }
    | IDENTIFIER    {
                        NSSFormals result = new NSSFormals();
                        result.parameters = new List<String>();
                        result.parameters.Add((String)$1);
                        result.type = 1;
                        $$ = result;
                    }
    | "(" identifiers "." IDENTIFIER ")"    {
                                                NSSFormals result = new NSSFormals();
                                                result.parameters = (List<String>)$2;
                                                result.parameters.Add((String)$4);
                                                result.type = 2;
                                                $$ = result;
                                            }
    ;

identifiers
    : IDENTIFIER    {
                        if (($$ == null) || !($$ is List<String>)) $$ = new List<String>();
                        ((List<String>)$$).Add((String)$1);
                    }
    | identifiers IDENTIFIER     {
                                    if (($$ == null) || !($$ is List<String>)) $$ = $1;
                                    ((List<String>)$$).Add((String)$2);
                                }
    ;

biding
    : "(" IDENTIFIER expression ")"    {
                                        $$ = new Binding((String)$2, (Expression)$3);
                                    }
    ;

bidings
    : biding    {
                    if (($$ == null) || !($$ is List<Binding>)) $$ = new List<Binding>();
                    ((List<Binding>)$$).Add((Binding)$1);
                }
    | bidings biding    {
                            if (($$ == null) || !($$ is List<Binding>)) $$ = $1;
                            ((List<Binding>)$$).Add((Binding)$2);
                        }
    ;

expression
    : datum {    
                $$ = Expression.Constant($1,$1.GetType());
            }

    | IDENTIFIER    {
                        $$ = Engine.get((String)$1);
                    }


    | "(" IDENTIFIER ")"    {
                                $$ = new NSSCallNode(new NSSSymbolNode((String)$2),new List<NSSTTreeNode>());                                                
                            } 
    | "(" SET IDENTIFIER expression ")"    {
                                            $$ = Engine.set((String)$3, (Expression)$4);
                                        }
    | "(" IF expression expression expression ")"    {
                                                        $$ = Engine.ifThen((Expression)$3, (Expression)$4, (Expression)$5);
                                                    }
    | "(" IF expression expression ")"    {
                                            $$ = Engine.ifThen((Expression)$3, (Expression)$4);
                                        }
    | "(" ID_QUOTE expression ")"    {
                                        $$ = new NSSQuotationNode(((NSSTTreeNode)$3).quotation)
                                        {
                                            quotation = "(quote " + ((NSSTTreeNode)$3).quotation + ")"
                                        };
                                    }
    | SINGLE_QUOTE expression    {
                                    $$ = new NSSQuotationNode(((NSSTTreeNode)$2).quotation)
                                    {
                                        quotation = "(quote " + ((NSSTTreeNode)$2).quotation + ")"
                                    };
                                }
    | "(" LAMBDA formals body ")"    {
                                                $$ = Engine.lambda((Body)$4,(NSSFormals)$3, _engine.environment._location);
                                            }
    | "(" CONDITIONAL cond_clauses else_clause ")"    {
                                                        if ($3 is NSSErrorNode) $$ = $3;
                                                        else if ($4 is NSSErrorNode) $$ = $4;
                                                        else $$ = new NSSDerivedConditionalNode((List<NSSCondClause>)$3, (List<NSSTTreeNode>)$4);
                                                        ((NSSTTreeNode)$$).quotation = "(" + (String)$2 + " " + ( ($3 is NSSErrorNode)? ((NSSTTreeNode)$3).quotation : NSSQuotationNode.quoteList((List<NSSTTreeNode>)$3)) + " else " + ( ($4 is NSSErrorNode)? ((NSSTTreeNode)$4).quotation : NSSQuotationNode.quoteList((List<NSSTTreeNode>)$4)) + ")";
                                                    }
    | "(" CONDITIONAL cond_clauses ")"    {
                                            if ($3 is NSSErrorNode) $$ = $3;
                                            else $$ = new NSSDerivedConditionalNode((List<NSSCondClause>)$3, null);
                                            ((NSSTTreeNode)$$).quotation = "(" + (String)$2 + " " + ( ($3 is NSSErrorNode)? ((NSSTTreeNode)$3).quotation : NSSQuotationNode.quoteList((List<NSSTTreeNode>)$3)) + ")";
                                        } 
    | "(" CASE expression case_clauses else_clause ")"    {
                                                            if ($3 is NSSErrorNode) $$ = $3;
                                                            else if ($4 is NSSErrorNode) $$ = $4;
                                                                 else if ($5 is NSSErrorNode) $$ = $5; 
                                                                       else $$ = new NSSCaseNode((NSSTTreeNode)$3, (List<NSSCaseClause>)$4, (List<NSSTTreeNode>)$5);
                                                            ((NSSTTreeNode)$$).quotation = "(" + (String)$2 + " " + ((NSSTTreeNode)$3).quotation + " " +
                                                                                    ( ($4 is NSSErrorNode)?((NSSTTreeNode)$4).quotation : NSSQuotationNode.quoteList((List<NSSCaseClause>)$4) ) + " " +
                                                                                    ( ($5 is NSSErrorNode)?((NSSTTreeNode)$5).quotation : NSSQuotationNode.quoteList((List<NSSTTreeNode>)$5) ) + ")";
                                                        }
    | "(" CASE expression case_clauses ")"    {
                                                if ($3 is NSSErrorNode) $$ = $3;
                                                else if ($4 is NSSErrorNode) $$ = $4;
                                                     else $$ = new NSSCaseNode((NSSTTreeNode)$3, (List<NSSCaseClause>)$4, null);
                                                ((NSSTTreeNode)$$).quotation = "(" + (String)$2 + " " + ((NSSTTreeNode)$3).quotation + " " +
                                                                            ( ($4 is NSSErrorNode)?((NSSTTreeNode)$4).quotation : NSSQuotationNode.quoteList((List<NSSCaseClause>)$4) ) + ")";
                                            }
    | "(" AND expressions ")"    {
                                    $$ = Engine.and((List<Expression>)$3);
                                }
    | "(" AND ")"    {
                        $$ = Engine.and(null);
                    }
    | "(" OR expressions ")"    {
                                    if ($3 is NSSErrorNode) $$ = $3;
                                    else $$ = new NSSOrNode((List<NSSTTreeNode>)$3);
                                    ((NSSTTreeNode)$$).quotation = "(" + (String)$2 + " " + ( ($3 is NSSErrorNode)?((NSSTTreeNode)$3).quotation : NSSQuotationNode.quoteList((List<NSSTTreeNode>)$3) ) + ")";
                                }
    | "(" OR ")"    {
                        $$ = new NSSOrNode(null)
                        { 
                            quotation = "(" + (String)$2 + ")" 
                        };
                    }
    | "(" BEGIN expressions ")"    {
                                    if ($3 is NSSErrorNode) $$ = $3;
                                    else $$ = new NSSBegin2Node(((List<NSSTTreeNode>)$3));
                                    ((NSSTTreeNode)$$).quotation = "(" + (String)$2 + " " + ( ($3 is NSSErrorNode)?((NSSTTreeNode)$3).quotation : NSSQuotationNode.quoteList((List<NSSTTreeNode>)$3) ) + ")";
                                }
    | "(" LET "(" bidings ")" body ")"    {
                                            $$ = Engine.let((List<Binding>)$4, (Body)$6);
                                        }
    | "(" LETREC "(" bidings ")" body ")"    {
                                                $$ = new NSSLetrecNode((List<NSSBinding>)$4, (List<NSSTTreeNode>)$6);
                                            }
    | "(" LETSTAR "(" bidings ")" body ")"    {
                                                $$ = Engine.let_((List<Binding>)$4, (Body)$6);
                                            }
    | "(" LETRECSTAR "(" bidings ")" body ")"    {
                                                    $$ = new NSSLetrecStarNode((List<NSSBinding>)$4, (List<NSSTTreeNode>)$6);
                                                }
    | "(" expression expressions ")"    {  
                                            if ($2 is Expression)
                                            {
                                                switch(((Expression)$2).NodeType)
                                                {
                                                    case ExpressionType.Lambda:
                                                        $$ = Engine.callProcedure((LambdaExpression)$2, (List<Expression>)$3, _engine);
                                                    break;
                                                    case ExpressionType.Call:
                                                        $$ = Engine.callProcedure((MethodCallExpression)$2, (List<Expression>)$3, _engine); 
                                                    break;
                                                    default:
                                                    break;                                                    
                                                }
                                                break;
                                                $$ = new NSSCallNode((NSSSymbolNode)$2,(List<NSSTTreeNode>)$3)
                                                {
                                                    quotation = "(" + ((NSSSymbolNode)$2).quotation + " " + NSSQuotationNode.quoteList( (List<NSSTTreeNode>)$3 ) + ")"
                                                };
                                                break;
                                            } 
                                            if ($2 is NSSLambdaNode)
                                            {
                                                $$ = new NSSCallNode((NSSLambdaNode)$2,(List<NSSTTreeNode>)$3);
                                                break;
                                            }
                                            Console.WriteLine("Won´t Break!"); 

                                        }
        //dtBoolean, dtNumeric, dtString, dtPair, dtList, dtVariable, dtConst, dtExpression, dtFunction, 
        //dtVector, dntVecto8, dntNETConst, dtNETInstance, dtNETEnum, dtNETStruct, dtNETClass,
        //dtNETProcedure, dtError, dtUnspecifed
    ;

expressions
    : expression    {    
                        if (($$ == null) || !($$ is List<Expression>)) $$ = new List<Expression>();
                        ((List<Expression>)$$).Add((Expression)$1);
                    }
    | expressions expression    {    
                                    ((List<Expression>)$1).Add((Expression)$2);
                                    $$ = ((List<Expression>)$1); 
                                }
    ;

//<datum> −> <lexeme datum>
//| <compound datum>
datum
    : lexeme_datum
    | compound_datum
    ;

//<lexeme datum> −> <boolean> | <number>'    
//| <character> | <string> | <symbol>
lexeme_datum
    : boolean    {    
                    $$ = $1;
                }
    | NUMBER    {
                    $$ = $1;
                }   
    | CHARACTER    {
                    $$ = $1;
                }
    | STRING    {    
                    $$ = $1;
                }
    ;

//<compound datum> −> <list> | <vector> | <bytevector>
compound_datum
    : vector
    | bytevector
    | list
    ;


/*
//<abbreviation> −> <abbrev prefix> <datum>
abbreviation
    : abbrev_prefix datum
    ;

//<abbrev prefix> −> ’ | ` | , | ,@
//| #’ | #` | #, | #,@
abbrev_prefix
    : QUOTEMARK
    | ","
    | ",@"
    | HASH_QUOTEMARK
    | "#'"
    | "#,"
    | "#,@"
    ;

*/

 

//<vector> −> #(<datum>*)
vector
    : "#(" expressions ")"
    ;

//<bytevector> −> #vu8(<u8>*)
bytevector
    : "#vu8(" u80M ")"
    ;

//<list> -> (<datum> <datum> <datum> <datum>)
list
    : "(" list_componets ")"    {
                                    $$ = new NSCPair((List<NSCDatum>)$2)
                                    {
                                        quotedText = "(" + NSSQuotationNode.quoteList((List<NSCDatum>)$2) + ")"
                                    };
                                }
    ;

list_componets
    : datum    {
                if (($$ == null) || !($$ is List<NSCDatum>)) $$ = new List<NSCDatum>();
                ((List<NSCDatum>)$$).Add((NSCDatum)$1);
            }
    | list_componets datum    {
                                if (($$ == null) || !($$ is List<NSCDatum>)) $$ = $1;                                
                                ((List<NSCDatum>)$$).Add((NSCDatum)$2);
                            }
    ;

//<u8> −> <any <number> representing an exact
//integer in {0, . . . , 255}>
u8
    : NUMBER
    ;

u80M
    :
    | u80M u8
    ;

boolean 
    : TRUE        
    | FALSE        
    ;

%%  

public void yyerror(string msg, params object[] args)
{
    Console.Write(msg);

}


public Parser(ScanBase scn, Context topLevel, Engine engine, bool debug):base(scn)
{
    Trace.Listeners.Add(new TextWriterTraceListener(Console.Out));
    Trace.AutoFlush = true;
    _topLevel = topLevel;
    _currentContext = topLevel;
    Context.deepLoop();
    NetSchemeBuiltin.installBuiltIn(_currentContext);
    _state = new Stack<NSCParserState>();
    _state.Push(NSCParserState.psNormal);
    _syntaxTree = null;
    _program = new NSSProgramNode();
    _engine = engine;
    _debug = debug;
}


// Start of user code