public static List<ILFunction> EmitProgram(L1Program program) { f_functionFindMap = new Dictionary<FunctionDefinition, ILFunction>(); f_ilProgram = new List<ILFunction>(); foreach (var fDef in program.Functions) { ILFunction ilFun = new ILFunction(); ilFun.ReturnType = fDef.Header.ReturnType; if (fDef.Header.ReturnType == null) { ilFun.IsVoidReturn = true; } ilFun.Name = fDef.Header.FunctionName; foreach (var p in fDef.Header.Parameters) { ilFun.Parameters.Add(p.Name); } if (fDef.IsEmbedded) { ilFun.EmbeddedBody = fDef.Body; bool t = !L1Runtime.DynamicResultAttribute.IsDynamic(fDef.Body); ilFun.CanBeCalculatedWithoutRun = t; } else { f_ilProgram.Add(ilFun); } f_functionFindMap.Add(fDef, ilFun); } foreach (var KV in f_functionFindMap) { if (KV.Key.IsEmbedded == false) { //EmitStatementList(KV.Key.Statements, KV.Value.Body); CurrentFunction = KV.Value; foreach (var p in KV.Key.Header.Parameters) { CurrentFunction.AddLocal(p.Name, p.Type); } _EmitStatementList(KV.Key.Statements, KV.Value.Body); KV.Value.Body = ReduceList(KV.Value.Body); CurrentFunction = null; } } MarkDynamicFunctions(); //Debug output foreach (var KV in f_functionFindMap) { if (KV.Key.IsEmbedded == false) { Console.WriteLine (String.Format(".specentry {0} {1}", KV.Value.Name, KV.Value.CanBeCalculatedWithoutRun ? "" : ".dynamic")); foreach (ILInstuction inst in KV.Value.Body) Console.WriteLine(String.Format("{0}\t\t{1}", inst.Line, inst)); Console.WriteLine(".end"); Console.WriteLine(""); Console.WriteLine (".f_calls " + KV.Value.Name); var fcalls = FindAllFunctionCalls(KV.Value); foreach (var fcall in fcalls) Console.WriteLine(String.Format("{0}", fcall)); Console.WriteLine(".end"); Console.WriteLine(""); } } return f_ilProgram; }
static void Interpret(L1Program program) { }
public static void InitStdFunctions(L1Program program) { Dictionary<FunctionHeader, MethodInfo> stdlib = new Dictionary<FunctionHeader, MethodInfo>(); Type runtimeContainer = typeof(L1Runtime.L1Stdlib); MethodInfo[] methods = runtimeContainer.GetMethods(BindingFlags.Static | BindingFlags.Public); foreach (MethodInfo mi in methods) { Attribute signatureAttrA = Attribute.GetCustomAttribute(mi, typeof(L1Runtime.SignatureAttribute), false); if (signatureAttrA != null) { L1Runtime.SignatureAttribute signatureAttr = (L1Runtime.SignatureAttribute)signatureAttrA; FunctionHeader fh = new FunctionHeader(mi.Name, GetVariableTypeByTypeId(signatureAttr.ReturnTypeId)); int i = 0; foreach (L1Runtime.VariableTypeId typeId in signatureAttr.ParametersTypeIds) { FunctionParameter p = new FunctionParameter("a"+i.ToString(), GetVariableTypeByTypeId(typeId)); System.Diagnostics.Debug.Assert(p.Type != null); fh.AddParameter(p); i++; } FunctionDefinition fdef = new FunctionDefinition(); fdef.Header = fh; fdef.IsEmbedded = true; fdef.Body = mi; fdef.Location = new LexLocation(); fdef.Statements = new StatementList(); program.AddFunctionToForward(fdef); stdlib.Add(fh, mi); } } EmitServices.DefineStandartFunctions(stdlib); }
public static void SemanticAnalise(L1Program program) { foreach (FunctionDefinition functionDef in program.Functions) { if (functionDef.IsEmbedded) continue; SymbolTableLight table = new SymbolTableLight(); foreach (FunctionParameter parameter in functionDef.Header.Parameters) { SymbolLight symbol = new SymbolLight(parameter.Name, parameter.Type); table.AddSymbol(symbol); } f_currentFunction = functionDef; CheckForLabelsDuplicates(f_currentFunction.Statements); ValidateStatementList(functionDef.Statements, table); if (functionDef.Header.ReturnType != null && !HasReturn(functionDef.Statements)) { CompilerServices.AddError( functionDef.Location, "Not all branches of execution return value" ); } } }
public static AssemblyBuilder GenerateAssembly(string name, L1Program program) { AssemblyName assemblyName = new AssemblyName(name); AssemblyBuilder assemblyBuilder = AppDomain.CurrentDomain.DefineDynamicAssembly(assemblyName, AssemblyBuilderAccess.RunAndSave); ModuleBuilder moduleBuilder = assemblyBuilder.DefineDynamicModule(assemblyName.ToString(), assemblyName + ".exe"); //Main method TypeBuilder mainTypeBuilder = moduleBuilder.DefineType("L1ProgramMain", TypeAttributes.Class | TypeAttributes.Public); MethodBuilder mainMethodBuilder = mainTypeBuilder.DefineMethod("Main", MethodAttributes.Public | MethodAttributes.Static); mainMethodBuilder.SetParameters(typeof(string[])); ILGenerator mainIlGenerator = mainMethodBuilder.GetILGenerator(); mainIlGenerator.Emit(OpCodes.Ldarg_0); mainIlGenerator.Emit(OpCodes.Call, f_mainRuntimeMethod); mainIlGenerator.Emit(OpCodes.Ret); //Program methods TypeBuilder functionsTypeBuilder = moduleBuilder.DefineType("L1ProgramFunctions", TypeAttributes.Class | TypeAttributes.Public); List<MethodBuilder> functionBuilders = new List<MethodBuilder>(); foreach (FunctionDefinition fDef in program.Functions) { if (fDef.IsEmbedded) continue; MethodBuilder functionBuilder = functionsTypeBuilder.DefineMethod(fDef.Header.FunctionName, MethodAttributes.Public | MethodAttributes.Static); if (fDef.Header.ReturnType != null) { Type t = GetTypeForCompilerType(fDef.Header.ReturnType); functionBuilder.SetReturnType(t); } else { functionBuilder.SetReturnType(typeof(void)); } List<Type> paramTypes = new List<Type>(); foreach (FunctionParameter parameter in fDef.Header.Parameters) { Type t = GetTypeForCompilerType(parameter.Type); paramTypes.Add(t); } functionBuilder.SetParameters(paramTypes.ToArray()); f_functions.Add(fDef.Header, functionBuilder); } foreach (FunctionDefinition fDef in program.Functions) { if (fDef.IsEmbedded) continue; MethodBuilder functionBuilder = (MethodBuilder)f_functions[fDef.Header]; ILGenerator ilGen = functionBuilder.GetILGenerator(); SymbolTable table = new SymbolTable(); int i = 0; foreach (FunctionParameter parameter in fDef.Header.Parameters) { Type t = GetTypeForCompilerType(parameter.Type); table.AddSymbol(parameter.Name, t, i++); } EmitFunction(fDef, table, ilGen); } //Завершение процесса генерации Type tMain = mainTypeBuilder.CreateType(); Type tFunctions = functionsTypeBuilder.CreateType(); moduleBuilder.CreateGlobalFunctions(); assemblyBuilder.SetEntryPoint(mainMethodBuilder, PEFileKinds.ConsoleApplication); return assemblyBuilder; }