public EnviromentFrame Extend(List <object> r) { var argCnt = Arity; var callEnv = new EnviromentFrame(En); foreach (var arg in Argument) { callEnv.Define(arg, r[--argCnt]); } return(callEnv); }
private void DefineMacro(Cons cons) { var macroName = cons.Car() as Symbol; var macro = cons.Cdr().Car() as Cons; if ((macro.Car() as Symbol)?.Name == "syntax-rules") { var syntaxRules = BuildSynataxRules(macro.Cdr() as Cons); Macro.Define(macroName, syntaxRules); } else { // unsuported } }
public static Cons MExpand(Cons seq) // TODO { var rseq = new Cons(); foreach (var o in seq.GetIterator()) { var exp = o.Car(); if (exp is Cons) { var op = exp.Car() as Symbol; var arguments = exp.Cdr() as Cons; if (op?.Name == "defmacro") { var mName = arguments?.Car().Car() as Symbol; var mArg = arguments?.Car().Cdr() as Cons; var mBody = arguments?.Cdr() as Cons; macro.Define(mName, new Macro(mArg, mBody)); continue; } else if (macro.Lookup(op)) { foreach (var o1 in (macro.Get(op).Expand(arguments)).GetIterator()) { rseq.Add(o1.Car()); } continue; } } rseq.Add(exp); } return(rseq); }
static object VM3(Operation operation, EnviromentFrame e) { object a = null; var x = operation; var rib = 0; var trueStack = new TrueStack(100); while (true) { switch (x.Cmd) { case Operation.Comand.Halt: return(a); case Operation.Comand.Refer: { a = e.Get(x.Var); x = x.Branch1; break; } case Operation.Comand.Constant: { a = x.Value; x = x.Branch1; break; } case Operation.Comand.Close: { a = new Closure(x.Branch2, e, x.Vars); x = x.Branch1; break; } case Operation.Comand.Test: { x = GetSBool(a) == false ? x.Branch2 : x.Branch1; break; } case Operation.Comand.Assign: { e.Set(x.Var, a); x = x.Branch1; break; } case Operation.Comand.Extend: { e.Define(x.Var, a); x = x.Branch1; break; } case Operation.Comand.Conti: { var var = "v".O3Symbol(); a = new Closure(Operation.Nuate(TrueStack.Clone(trueStack), var), new EnviromentFrame(), new [] { var }); x = x.Branch1; break; } case Operation.Comand.Nuate: { trueStack = TrueStack.Clone(x.Value as TrueStack); a = e.Get(x.Var); x = Operation.Return(); break; } case Operation.Comand.Frame: { trueStack.Push(rib); trueStack.Push(e); trueStack.Push(x.Branch2); x = x.Branch1; rib = 0; break; } case Operation.Comand.Argument: { trueStack.Push(a); x = x.Branch1; rib++; break; } case Operation.Comand.Apply: { if (a is MulticastDelegate) { var func = a as MulticastDelegate; var parameters = func.Method.GetParameters(); var argCnt = 0; var cArg = new List <object>(); foreach (var pi in parameters) { if (typeof(Params) == pi.ParameterType) { var par = new Params(); while (argCnt++ < rib) { par.Add(trueStack.Pop()); } cArg.Add(par); } else { if (argCnt++ < rib) { cArg.Add(trueStack.Pop()); } } } if (parameters.Length != cArg.Count) { throw new Exception($"Arity mismatch {func}, expected {parameters.Length}, given {cArg.Count} arguments"); } a = func.DynamicInvoke(cArg.ToArray()); x = Operation.Return(); break; } if (a is Closure) { var func = a as Closure; x = func.Body; e = new EnviromentFrame(func.En); if (rib != func.Argument.Length) { throw new Exception($"Arity mismatch, expected {func.Argument.Length}, given {rib} arguments"); } foreach (var arg in func.Argument) { e.Define(arg, trueStack.Pop()); } rib = 0; break; } throw new Exception($"{a} is not a callable"); } case Operation.Comand.Return: { x = trueStack.Pop() as Operation; e = trueStack.Pop() as EnviromentFrame; rib = (int)trueStack.Pop(); break; } } } }