public object Interpret(object exp) { IASTNode node = ASTCompiler.Compile(null, ListProcess.TransformLibraryForms(exp)); ReserveGlobalVaraible(SymbolTable.GetGlobalSymbolCount()); ASTNode_Lambda lambdaNode = new ASTNode_Lambda { bodyNode = node, bodyFreeAddresses = new List <FreeAddress>(), childrenFreeAddresses = new List <FreeAddress>(), formalCount = 0, locals = new List <string>(), }; var fileName = "____test.exe"; var assemblyBuilder = AppDomain.CurrentDomain.DefineDynamicAssembly( new AssemblyName(GenernateUniqueString("assemly")), AssemblyBuilderAccess.RunAndSave); var moduleBuilder = assemblyBuilder.DefineDynamicModule(GenernateUniqueString("module"), fileName, HasSymbolInfo()); var envTypeBuilder = moduleBuilder.DefineType(GenernateUniqueString("class")); var methodBuilder = new ASTNodeVisitor_JITCompiler(null, envTypeBuilder, lambdaNode).MethodBuilder; var type = envTypeBuilder.CreateType(); assemblyBuilder.SetEntryPoint(methodBuilder, PEFileKinds.ConsoleApplication); // assemblyBuilder.Save(fileName); return(((Func <object>)type.GetMethod(methodBuilder.Name).CreateDelegate(typeof(Func <object>)))()); }
public object Interpret(object exp) { IASTNode node = ASTCompiler.Compile(null, ListProcess.TransformLibraryForms(exp)); Env.ReserveGlobalVariables(SymbolTable.GetGlobalSymbolCount()); return(new ASTNodeVisitor_Interpreter(null, node).Value); }
static void Main(string[] args) { var tokens = Parser.Tokenize(new System.IO.StreamReader("../../test.rkt").ReadToEnd()); while (true) { object s = Parser.Parse(tokens); if (s == null) { break; } object v = JITInterpreter_DS2.Instance().Interpret(s); // object v = JITInterpreter_DS.Instance().Interpret(s); // object v = ASTInterpreter.Instance().Interpret(s); if (v != null) { ListProcess.PrintPairExp(v); } } }
private JITInterpreter_DS() { Utils.QueryPerformanceCounter(out mTimerStart); Utils.QueryPerformanceFrequency(out mTimerFreq); Dictionary <string, object> builtinVars = new Dictionary <string, object>() { { "true", true }, { "false", false }, { "else", true }, { "null", null }, }; Dictionary <string, object> builtinProcedures = new Dictionary <string, object>() { { "not", (Func <object, object>)(a => !(bool)a) }, { "identity", (Func <object, object>)(a => a) }, { "sqr", (Func <object, object>)(a => { var v = (INumber)a; return(v.Mul(v)); }) }, { "+", (Func <object, object, object>)((a, b) => ((INumber)a).Add((INumber)b)) }, { "-", (Func <object, object, object>)((a, b) => ((INumber)a).Sub((INumber)b)) }, { "*", (Func <object, object, object>)((a, b) => ((INumber)a).Mul((INumber)b)) }, { "/", (Func <object, object, object>)((a, b) => ((INumber)a).Div((INumber)b)) }, { "quotient", (Func <object, object, object>)((a, b) => ((INumber)a).Div((INumber)b).CastToInteger()) }, { "remainder", (Func <object, object, object>)((a, b) => ((INumber)a).Mod((INumber)b)) }, { "=", (Func <object, object, object>)((a, b) => ((INumber)a).CompareTo((INumber)b) == 0) }, { "<", (Func <object, object, object>)((a, b) => ((INumber)a).CompareTo((INumber)b) < 0) }, { "<=", (Func <object, object, object>)((a, b) => ((INumber)a).CompareTo((INumber)b) <= 0) }, { ">", (Func <object, object, object>)((a, b) => ((INumber)a).CompareTo((INumber)b) > 0) }, { ">=", (Func <object, object, object>)((a, b) => ((INumber)a).CompareTo((INumber)b) >= 0) }, { "eq?", (Func <object, object, object>)((a, b) => object.ReferenceEquals(a, b)) }, { "equal?", (Func <object, object, object>)((a, b) => object.Equals(a, b)) }, { "cons", (Func <object, object, object>)((a, b) => new Pair() { Car = a, Cdr = b }) }, { "car", (Func <object, object>)(a => ((Pair)a).Car) }, { "cdr", (Func <object, object>)(a => ((Pair)a).Cdr) }, { "drop", (Func <object, object, object>)((a, b) => { Pair l = (Pair)a; int n = ((NumberInteger)b).value; for (; n > 0; --n) { l = (Pair)l.Cdr; } return(l); }) }, { "length", (Func <object, object>)(a => { int n = 0; for (Pair l = (Pair)a; l != null; ++n, l = (Pair)l.Cdr) { ; } return(Number.Create(n)); }) }, { "append", (Func <object, object, object>)((a, b) => { var l = ListProcess.PairToList((Pair)a); return(ListProcess.ConcatListAndPairToNewPair(l, (Pair)b)); }) }, { "empty?", (Func <object, object>)(a => a == null) }, { "void", (Func <object>)(() => null) }, { "pretty-print", (Func <object, object>)(a => { ListProcess.PrintPairExp(a); return(null); }) }, { "display", (Func <object, object>)(a => { ListProcess.PrintListExp(ListProcess.PairExpToListExp(a)); return(null); }) }, { "current-inexact-milliseconds", (Func <object>)(() => { long now; Utils.QueryPerformanceCounter(out now); return(Number.Create((decimal)(now - mTimerStart) * 1000 / mTimerFreq)); }) }, { "exit", (Func <object>)(() => { Environment.Exit(0); return(null); }) }, { "random", (Func <object, object>)(a => Number.Create(mRandom.Next(((NumberInteger)a).value))) }, { "eval", (Func <object, object>)(a => { return(Instance().Interpret(ListProcess.PairExpToListExp(a))); }) }, }; ReserveGlobalVaraible(builtinVars.Count + builtinProcedures.Count); foreach (KeyValuePair <string, object> kv in builtinVars) { mGlobalVariables[SymbolTable.DefineOrGetGlobalSymbol(kv.Key).index] = kv.Value; } foreach (KeyValuePair <string, object> kv in builtinProcedures) { mGlobalVariables[SymbolTable.DefineOrGetGlobalSymbol(kv.Key).index] = kv.Value; } }
static public IASTNode Compile(SymbolTable symTable, object exp) { if (exp is string) { return(new ASTNode_GetVar { address = SymbolTable.Lookup(symTable, (string)exp) }); } else if (exp is INumber) { return(new ASTNode_Literal { value = exp }); } List <object> form = exp as List <object>; switch (form[0] as string) { case "quote": return(new ASTNode_Literal { value = ListProcess.ListExpToPairExp(form[1]) }); case "if": return(new ASTNode_If { predNode = Compile(symTable, form[1]), thenNode = Compile(symTable, form[2]), elseNode = Compile(symTable, form[3]) }); case "begin": return(new ASTNode_Begin { nodes = form.Skip(1).Select(e => Compile(symTable, e)).ToList() }); case "lambda": { SymbolTable newSymTable = new SymbolTable(symTable); var formals = ((List <object>)form[1]).Cast <string>(); foreach (var name in formals) { newSymTable.DefineLocalSymbol(name); } List <string> defines = new List <string>(); ListProcess.FindDefinition(defines, (List <object>)form[2], 1); foreach (var name in defines) { newSymTable.DefineLocalSymbol(name); } IASTNode body = Compile(newSymTable, form[2]); var finder = new ASTNodeVisitor_FindFreeAddresses(body); return(new ASTNode_Lambda { formalCount = ((List <object>)form[1]).Count, locals = formals.Concat(defines).ToList(), bodyNode = body, bodyFreeAddresses = finder.BodyFreeAddresses.ToList(), childrenFreeAddresses = finder.ChildrenFreeAddresses.ToList(), }); } case "define": case "set!": return(new ASTNode_SetVar { address = SymbolTable.Lookup(symTable, (string)form[1]), rightNode = Compile(symTable, form[2]) }); default: return(new ASTNode_Application { procedureNode = Compile(symTable, form[0]), actualNodes = form.Skip(1).Select(e => Compile(symTable, e)).ToList(), }); } }
private ASTInterpreter() { Utils.QueryPerformanceCounter(out sTimerStart); Utils.QueryPerformanceFrequency(out sTimerFreq); Dictionary <string, object> builtinVars = new Dictionary <string, object>() { { "true", true }, { "false", false }, { "else", true }, { "null", null }, }; Dictionary <string, Procedure> builtinProcedures = new Dictionary <string, Procedure>() { { "not", (args) => !(bool)args[0] }, { "identity", (args) => args[0] }, { "sqr", (args) => { var a = args[0] as INumber; return(a.Mul(a)); } }, { "+", (args) => ((INumber)args[0]).Add((INumber)args[1]) }, { "-", (args) => ((INumber)args[0]).Sub((INumber)args[1]) }, { "*", (args) => ((INumber)args[0]).Mul((INumber)args[1]) }, { "/", (args) => ((INumber)args[0]).Div((INumber)args[1]) }, { "quotient", (args) => ((INumber)args[0]).Div((INumber)args[1]).CastToInteger() }, { "remainder", (args) => ((INumber)args[0]).Mod((INumber)args[1]) }, { "=", (args) => (args[0].Equals(args[1])) }, { "<", (args) => (args[0] as IComparable).CompareTo(args[1]) < 0 }, { "<=", (args) => (args[0] as IComparable).CompareTo(args[1]) <= 0 }, { ">", (args) => (args[0] as IComparable).CompareTo(args[1]) > 0 }, { ">=", (args) => (args[0] as IComparable).CompareTo(args[1]) >= 0 }, { "eq?", (args) => object.ReferenceEquals(args[0], args[1]) }, { "cons", (args) => new Pair() { Car = args[0], Cdr = args[1] } }, { "car", (args) => ((Pair)args[0]).Car }, { "cdr", (args) => ((Pair)args[0]).Cdr }, { "drop", (args) => { Pair l = (Pair)args[0]; int n = ((NumberInteger)args[1]).value; for (; n > 0; --n) { l = (Pair)l.Cdr; } return(l); } }, { "length", (args) => { int n = 0; for (Pair l = (Pair)args[0]; l != null; ++n, l = (Pair)l.Cdr) { ; } return(Number.Create(n)); } }, { "append", (args) => { var l = ListProcess.PairToList((Pair)args[0]); l.InsertRange(l.Count, ListProcess.PairToList((Pair)args[1])); return(ListProcess.ListToPair(l)); } }, { "empty?", (args) => args[0] == null }, { "pretty-print", (args) => { ListProcess.PrintPairExp(args[0]); return(null); } }, { "display", (args) => { ListProcess.PrintListExp(ListProcess.PairExpToListExp(args[0])); return(null); } }, { "current-inexact-milliseconds", (args) => { long now; Utils.QueryPerformanceCounter(out now); return(Number.Create((decimal)(now - sTimerStart) * 1000 / sTimerFreq)); } }, { "exit", (args) => { Environment.Exit(0); return(null); } }, { "random", (args) => Number.Create(sRandom.Next(((NumberInteger)args[0]).value)) }, { "eval", (args) => Instance().Interpret(ListProcess.PairExpToListExp(args[0])) }, }; Env.ReserveGlobalVariables(builtinVars.Count + builtinProcedures.Count); foreach (KeyValuePair <string, object> kv in builtinVars) { Env.DefineBuiltin(SymbolTable.DefineOrGetGlobalSymbol(kv.Key), kv.Value); } foreach (KeyValuePair <string, Procedure> kv in builtinProcedures) { Env.DefineBuiltin(SymbolTable.DefineOrGetGlobalSymbol(kv.Key), kv.Value); } }