void CompileSexpr(SexprNode sexpr, NodeListParser nlp) { Logger.WriteLine(4, "CompileSexpr {0} <{1}>", sexpr, nlp); var snlp = NodeListParser.Create(sexpr.Args, Symbols); _currentparser = snlp; // intrinsics with individual parser and code generator if (sexpr.Sym.IsControl) { if (_controllookup.ContainsKey(sexpr.Sym.Keyword)) { _controllookup[sexpr.Sym.Keyword](sexpr.Sym, snlp, this); } else { nlp.Unexpected("unknown control function"); } } else { CompileBuiltin(sexpr.Sym as BuiltinSymbol, snlp); } }
// Compile a literal, symbol or expression that returns a typed value // Return datatype to caller for type checking DataTypes CompileValue(Type type, NodeListParser nlp) { Logger.WriteLine(4, "CompileValue {0} <{1}>", type, nlp); // bracketed expression with arguments if (nlp.IsSexpr) { var sexpr = nlp.GetSexprNode(); CompileSexpr(sexpr, nlp); return(sexpr.DataType); } if (nlp.IsFunc) { // bare function no arguments var sym = nlp.GetIdent().Sym as BuiltinSymbol; CompileBuiltin(sym, NodeListParser.Null); return(sym.DataType); } if (nlp.IsVariable) { var sym = nlp.GetIdent().Sym; _gen.EmitLoadVar(sym); return(sym.DataType); } if (nlp.IsAttribute || (nlp.IsList && nlp.CheckedHead.IsAttribute)) { var handler = Symbols.Find("--attribute") as BuiltinSymbol; if (handler != null) { CompileBuiltin(handler, nlp.GetParser()); } else { nlp.Syntax("attribute not allowed here"); } return(handler.DataType); } var func = _typeactiondict.SafeLookup(type); if (func != null) { // direct lookup to get constant value var value = func(type, nlp, this) as TypedValue; _gen.EmitLoadValue(value); return(value.DataType); } nlp.Unexpected("unknown type {0}", type); return(DataTypes.Unknown); }
// compile a prog block inside an existing scope internal void CompileProg(NodeListParser nlp) { Logger.WriteLine(2, "CompileProg <{0}>", nlp); // iterate over the action items in the prog block while (!nlp.Done) { // value -- special handler if (nlp.IsValue || nlp.IsValueCallable) { if (!CompileHandler("--value", nlp)) { nlp.Syntax("bare value not allowed"); } // callable function, call it } else if (nlp.IsCallable) { if (nlp.IsFunc && nlp.CurrentIdent.Sym.Keyword == Keywords.ELSE) { return; // sneaky! } var sexpr = nlp.GetSexprNode(); nlp.Expect(sexpr.DataType == DataTypes.Void, "void function"); CompileSexpr(sexpr, nlp); // list -- special handler } else if (nlp.IsList) { var handler = Symbols.Find("--list") as BuiltinSymbol; if (handler != null) { CompileBuiltin(handler, nlp.GetParser()); } else { nlp.Unexpected("unknown function"); } } else { nlp.Expected("function call"); } } }