2003-10-24 cesar lopez nataren <cesar@ciencias.unam.mx>
authorCésar Natarén <cesar@mono-cvs.ximian.com>
Sat, 25 Oct 2003 00:45:38 +0000 (00:45 -0000)
committerCésar Natarén <cesar@mono-cvs.ximian.com>
Sat, 25 Oct 2003 00:45:38 +0000 (00:45 -0000)
* ast.cs: Added 'virtual' Emit method (I might change it to be
abstract, but I would have to added to all classes that derive
from it. I'll do it later)
* Block.cs: Added Emit method.
* CodeGnerator.cs: Restructured it (not based on the Visitor pattern
anymore) - still missing some methods, ut on the way. A nice
hacking weekend coming. Added EmitContext class.
* ScriptBlock.cs: Added Emit method.
* VariableDeclaration.cs: Changed type field from string to
Type. Added Emit method.
* VariableStatement.cs: Added Emit method.
* driver.cs: Added CodeGeneration phase (only simple var
declarations support it. More coming soon).

svn path=/trunk/mcs/; revision=19367

mcs/class/Microsoft.JScript/Microsoft.JScript/Block.cs
mcs/class/Microsoft.JScript/Microsoft.JScript/ChangeLog
mcs/class/Microsoft.JScript/Microsoft.JScript/CodeGenerator.cs
mcs/class/Microsoft.JScript/Microsoft.JScript/ScriptBlock.cs
mcs/class/Microsoft.JScript/Microsoft.JScript/VariableDeclaration.cs
mcs/class/Microsoft.JScript/Microsoft.JScript/VariableStatement.cs
mcs/class/Microsoft.JScript/Microsoft.JScript/ast.cs
mcs/class/Microsoft.JScript/Microsoft.JScript/driver.cs

index b9a729122d2908c20990fc73515c5f7118533f4e..07dfb09ee1ca0d526e21596512a7bd627a5f023d 100644 (file)
@@ -37,5 +37,13 @@ namespace Microsoft.JScript {
 
                        return sb.ToString ();
                }
+
+               internal override void Emit (EmitContext ec)
+               {
+                       int i, size = Elements.Count;
+
+                       for (i = 0; i < size; i++)
+                               ((AST) Elements [i]).Emit (ec);
+               }                                               
        }
-}
\ No newline at end of file
+}
index 4db10e38725b50ea2c6a8e29ebd1363adf7a9b94..16185b3b79b59f7b2ba16399683f248b0b973de8 100644 (file)
@@ -1,3 +1,20 @@
+2003-10-24  cesar lopez nataren <cesar@ciencias.unam.mx>
+
+       * ast.cs: Added 'virtual' Emit method (I might change it to be
+       abstract, but I would have to added to all classes that derive
+       from it. I'll do it later)
+       * Block.cs: Added Emit method.
+       * CodeGnerator.cs: Restructured it (not based on the Visitor pattern
+       anymore) - still missing some methods, ut on the way. A nice
+       hacking weekend coming. Added EmitContext class.
+       * ScriptBlock.cs: Added Emit method.
+       * VariableDeclaration.cs: Changed type field from string to
+       Type. Added Emit method.
+       * VariableStatement.cs: Added Emit method.
+       * driver.cs: Added CodeGeneration phase (only simple var
+       declarations support it. More coming soon).
+
+
 2003-10-22  cesar lopez nataren <cesar@ciencias.unam.mx>
 
        * statement.cs: added Return class.
        x = factorial (4); 
        print (x);
 
-       As you can see, it's not the classical factorial function
+       As you can see, it's not the classic factorial function
        definition, I still have to make some tricks like storing the
        result from the recursive call and then multiply. But this new
        grammar it's easier to alter than the old one. Also we got support
        for for-in statements, for statements, global expressions, support
-       for object accesors or better known as the "dot" operator. Too
+       for object accesors or better known as the "dot" operator. Two
        rules are on the eye: left_hand_size_expr and call_expr, in order
        to finish the parsing grammar and fix the bugs.
 
index 59d4dcf8b8aafccefe5804d5769863cb77ba69ec..e1945482733ce82450627d7a1014a01b6efea193 100644 (file)
@@ -1,5 +1,5 @@
 //
-// CodeGenerator.cs: The actual IL code generator for JScript .Net programs.
+// CodeGenerator.cs
 //
 // Author:
 //     Cesar Lopez Nataren (cesar@ciencias.unam.mx)
 using System;
 using System.Reflection;
 using System.Reflection.Emit;
-using System.Runtime.CompilerServices;
-using Microsoft.JScript.Vsa;
+using System.Threading;
 
-namespace Microsoft.JScript.Tmp {
+namespace Microsoft.JScript {
 
-       internal sealed class CodeGenerator {
+       internal class EmitContext {
 
-               internal AssemblyName assemblyName;
-               internal AssemblyBuilder assemblyBuilder;
-               internal ModuleBuilder moduleBuilder;
-               internal TypeBuilder typeBuilder;
-               internal ILGenerator ilGen;
+               internal TypeBuilder type_builder;
 
-               internal string MODULE_NAME = "JScript Module";
-               internal string GLOBAL_SCOPE = "Microsoft.JScript.GlobalScope";
-       
-               internal CodeGenerator (string assemName, AssemblyBuilderAccess access)
+               internal EmitContext (TypeBuilder type)
                {
-                       assemblyName = new AssemblyName ();
-                       assemblyName.Name = assemName;
-
-                       AppDomain appDomain = AppDomain.CurrentDomain;
-                       
-                       this.assemblyBuilder = appDomain.DefineDynamicAssembly (assemblyName, 
-                                                                               access);
-
-                       this.moduleBuilder = assemblyBuilder.DefineDynamicModule (MODULE_NAME,
-                                                                                 assemblyName.Name + ".exe", false);
-               }
-
-
-               internal void EmitJScript0Type ()
-               {
-                       this.typeBuilder = moduleBuilder.DefineType ("JScript 0",
-                                                                    TypeAttributes.Class |
-                                                                    TypeAttributes.Public);
-
-                       this.typeBuilder.SetParent (typeof (Microsoft.JScript.GlobalScope));
-
-                       CustomAttributeBuilder attr;
-                       Type t = typeof (CompilerGlobalScopeAttribute);
-                       attr = new CustomAttributeBuilder (t.GetConstructor (new Type [] {}), 
-                                                                            new object [] {});
-                       this.typeBuilder.SetCustomAttribute (attr);
-               }
-
-
-               internal void EmitJScript0Cons ()
-               {
-                       ConstructorBuilder consBuilder;
-
-                       consBuilder = typeBuilder.DefineConstructor (MethodAttributes.Public,
-                                                                    CallingConventions.Standard,
-                                                                    new Type [] {typeof (Microsoft.JScript.GlobalScope)});
-
-                       this.ilGen = consBuilder.GetILGenerator ();
-
-                       this.ilGen.Emit (OpCodes.Ldarg_0);
-                       this.ilGen.Emit (OpCodes.Ldarg_1);
-                       this.ilGen.Emit (OpCodes.Dup);
-                       this.ilGen.Emit (OpCodes.Ldfld, 
-                                        typeof (Microsoft.JScript.ScriptObject).GetField ("engine"));
-                       this.ilGen.Emit (OpCodes.Call,
-                                        typeof (Microsoft.JScript.GlobalScope).GetConstructor (new Type [] {typeof (Microsoft.JScript.GlobalScope), typeof (Microsoft.JScript.Vsa.VsaEngine)}));
-                       this.ilGen.Emit (OpCodes.Ret);
-               }
-
-
-               private void EmitJScript0GlobalCode (ASTList program)
-               {
-                       MethodBuilder methodBuilder;
-                       methodBuilder = this.typeBuilder.DefineMethod ("Global Code",
-                                                                       MethodAttributes.Public, 
-                                                                       typeof (object), 
-                                                                       null);
-                        
-                       this.ilGen = methodBuilder.GetILGenerator ();
-                        
-                       this.ilGen.Emit (OpCodes.Ldarg_0);
-
-                       this.ilGen.Emit (OpCodes.Ldfld,
-                                        typeof (Microsoft.JScript.ScriptObject).GetField ("engine"));
-                
-                       this.ilGen.Emit (OpCodes.Ldarg_0);
-
-                       this.ilGen.Emit (OpCodes.Call, 
-                                        typeof (Microsoft.JScript.Vsa.VsaEngine).GetMethod ("PushScriptObject", new Type [] {typeof (Microsoft.JScript.ScriptObject)}));
-
-
-                       // program.Visit (this, null);
-                       
-                       
-                       this.ilGen.Emit (OpCodes.Ldsfld, 
-                                        typeof (Microsoft.JScript.Empty).GetField ("Value"));
-
-                       this.ilGen.Emit (OpCodes.Ldarg_0);
-
-                       this.ilGen.Emit (OpCodes.Ldfld, 
-                                        typeof (Microsoft.JScript.ScriptObject).GetField ("engine"));
-
-                       this.ilGen.Emit (OpCodes.Call,
-                                       typeof (Microsoft.JScript.Vsa.VsaEngine).GetMethod ("PopScriptObject"));
-
-                       this.ilGen.Emit (OpCodes.Pop);
-                       this.ilGen.Emit (OpCodes.Ret);                       
-                }
-
-
-
-       
-               public void EmitJScript0 (ASTList program)
-               {
-                       this.EmitJScript0Type ();
-                       this.EmitJScript0Cons ();
-                       this.EmitJScript0GlobalCode (program);
-                       
-                       this.typeBuilder.CreateType ();
-               }                                       
-                                                                           
-
-               //
-               // JScript Main class construction
-               //
-
-               private void EmitJScriptMainType ()
-                {
-                       this.typeBuilder = moduleBuilder.DefineType ("JScript Main", 
-                                                               TypeAttributes.Public);
-
-                       this.typeBuilder.SetParent (typeof (System.Object));
-                }
-
-
-                private void EmitJScriptMainCons ()
-                {
-                        ConstructorBuilder consBuilder;
-                        consBuilder = typeBuilder.DefineConstructor (MethodAttributes.Public, 
-                                                                     CallingConventions.Standard,
-                                                                      new Type [] {});
-
-                       this.ilGen = consBuilder.GetILGenerator ();
-                       this.ilGen.Emit (OpCodes.Ldarg_0);
-                       this.ilGen.Emit (OpCodes.Call, 
-                                         typeof (Object).GetConstructor (new Type [] {}));
-                       this.ilGen.Emit (OpCodes.Ret);
-                }
-                        
-
-                private void EmitJScriptMainFunction ()
-                {
-                       MethodBuilder methodBuilder;
-                       methodBuilder = typeBuilder.DefineMethod ("Main", 
-                                                                  MethodAttributes.Public | 
-                                                                  MethodAttributes.Static, 
-                                                                  typeof (void),
-                                                                  new Type [] {typeof (String [])});
-                        
-                        methodBuilder.SetCustomAttribute (new CustomAttributeBuilder 
-                                                          (typeof (STAThreadAttribute).GetConstructor (new Type [] {}),
-                                                           new object [] {}));
-
-
-                        this.ilGen = methodBuilder.GetILGenerator ();
-
-                        // declare local vars
-                        this.ilGen.DeclareLocal (typeof (Microsoft.JScript.GlobalScope));
-
-                        this.ilGen.Emit (OpCodes.Ldc_I4_1);
-                        this.ilGen.Emit (OpCodes.Ldc_I4_1);
-                        this.ilGen.Emit (OpCodes.Newarr, typeof (string));
-                        this.ilGen.Emit (OpCodes.Dup);
-                        this.ilGen.Emit (OpCodes.Ldc_I4_0);
-                        this.ilGen.Emit (OpCodes.Ldstr,
-                                         "mscorlib, Version=1.0.3300.0, Culture=neutral, Pub" + "licKeyToken=b77a5c561934e089");
-                        this.ilGen.Emit (OpCodes.Stelem_Ref);
-                        this.ilGen.Emit (OpCodes.Call,
-                                         typeof (Microsoft.JScript.Vsa.VsaEngine).GetMethod  ("CreateEngineAndGetGlobalScope", new Type [] {typeof (bool), typeof (string [])}));
-                        
-                        this.ilGen.Emit (OpCodes.Stloc_0);
-                        this.ilGen.Emit (OpCodes.Ldloc_0);
-                        
-
-                        this.ilGen.Emit (OpCodes.Newobj,
-                                         assemblyBuilder.GetType ("JScript 0").GetConstructor (new Type [] {typeof (Microsoft.JScript.GlobalScope)})); 
-
-                        this.ilGen.Emit (OpCodes.Call, assemblyBuilder.GetType ("JScript 0").GetMethod ("Global Code", new Type [] {}));
-
-                        this.ilGen.Emit (OpCodes.Pop);
-                        this.ilGen.Emit (OpCodes.Ret);
-
-                        this.assemblyBuilder.SetEntryPoint (methodBuilder);
-
-                }                        
-
-                public void EmitJScriptMain ()
-                {                        
-                        this.EmitJScriptMainType ();
-                        this.EmitJScriptMainCons ();
-                        this.EmitJScriptMainFunction ();
-
-                        Type t2 = this.typeBuilder.CreateType ();
-                }
-
-
-
-
-               // 
-               // Visitor methods, that Emit IL OpCodes for each type of 
-               // language constructs.
-               //
-
-               public object VisitASTList (ASTList prog, object obj)
-               {
-                       int size = prog.elems.Count;
-
-                       // for (int i = 0; i < size; i++)
-                               // ((AST) prog.elems [i]).Visit (this, obj);
-
-                       return null;
-               }
-
-
-               public object VisitVariableDeclaration (VariableDeclaration decl, 
-                                                       object args)
-               {
-                       throw new NotImplementedException ();
-               }
-
-
-               public object VisitFunctionDeclaration (FunctionDeclaration decl,
-                                                       object args)
-               {
-                       throw new NotImplementedException ();
-               }
-
-               
-               public object VisitBlock (Block b, object args)
-               {
-                       throw new NotImplementedException ();
-               }
-
-               
-               public object VisitEval (Eval e, object args)
-               {       
-                       throw new NotImplementedException ();
-               }
-
-               
-               public object VisitForIn (ForIn forIn, object args)
-               {
-                       throw new NotImplementedException ();
+                       type_builder = type;
                }
+       }
 
+       public class CodeGenerator {
 
-               public object VisitFunctionExpression (FunctionExpression fexp, 
-                                                      object args)
-               {
-                       throw new NotImplementedException ();
-               }
+               private static string MODULE = "JScript Module";
 
+               internal static string mod_name;
+               internal static AppDomain app_domain;
+               internal static AssemblyName assembly_name;
+               internal static AssemblyBuilder assembly_builder;
+               internal static ModuleBuilder module_builder;
 
-               public object VisitImport (Import imp, object args)
+               internal static void Init (string file_name)
                {
-                       throw new NotImplementedException ();
-               }
+                       app_domain = Thread.GetDomain ();
 
+                       assembly_name = new AssemblyName ();
+                       assembly_name.Name =  trim_extension (file_name);
 
-               public object VisitPackage (Package pkg, object args)
-               {
-                       throw new NotImplementedException ();
-               }
+                       mod_name = MODULE;
 
+                       assembly_builder = app_domain.DefineDynamicAssembly (
+                                            assembly_name,
+                                            AssemblyBuilderAccess.RunAndSave);
 
-               public object VisitScriptBlock (ScriptBlock sblock, object args)
-               {
-                       throw new NotImplementedException ();
+                       module_builder = assembly_builder.DefineDynamicModule (
+                                               mod_name,
+                                               assembly_name.Name + ".exe", 
+                                               false);
                }
 
-
-               public object VisitThrow (Throw t, object args)
+               internal static string trim_extension (string file_name)
                {
-                       throw new NotImplementedException ();
-               }
-
+                       int index = file_name.IndexOf ('.');
 
-               public object VisitTry (Try t, object args)
-               {
-                       throw new NotImplementedException ();
+                       if (index < 0)
+                               return file_name;
+                       else
+                               return file_name.Substring (0, index);
                }
 
-
-               public object VisitWith (With w, object args)
+               internal static void Save (string target_name)
                {
-                       throw new NotImplementedException ();
+                       assembly_builder.Save (target_name);
                }
 
-
-               public object VisitPrint (Print p, object args)
+               internal static void Emit (AST prog)
                {
-                       StringLiteral sl = p.Exp as StringLiteral;
+                       if (prog == null)
+                               return;
 
-                       // sl.Visit (this, args);
+                       TypeBuilder type_builder;
+                       type_builder = module_builder.DefineType ("JScript 0");
 
-                       this.ilGen.Emit (OpCodes.Call,
-                                        typeof (Microsoft.JScript.ScriptStream).GetMethod ("WriteLine", new Type [] {typeof (string)}));
+                       EmitContext ec = new EmitContext (type_builder);
 
-                       return null;
-               }
+                       prog.Emit (ec);
 
-
-               //
-               // Literals
-               //
-
-               public object VisitArrayLiteral (ArrayLiteral al, object args)
-               {
-                       throw new NotImplementedException ();
+                       ec.type_builder.CreateType ();
                }
 
-
-               public object VisitStringLiteral (StringLiteral sl, object args)
+               public static void Run (string file_name, AST prog)
                {
-                       this.ilGen.Emit (OpCodes.Ldstr, sl.Str);
+                       CodeGenerator.Init (file_name);
+                       CodeGenerator.Emit (prog);
 
-                       return null;
-               }
+                       CodeGenerator.Save (trim_extension (file_name) + 
+                                           ".exe");
+               }       
        }
 }
index a80f02f112acf63907483097f95349b9aa31eddf..7f50d7ff31fef82d7b3571c8e372218586f78390 100644 (file)
@@ -26,5 +26,10 @@ namespace Microsoft.JScript {
                {
                        return src_elems.ToString ();
                }
+
+               internal override void Emit (EmitContext ec)
+               {
+                       src_elems.Emit (ec);
+               }
        }
 }
\ No newline at end of file
index fb3b52cdeb9729fc84ca2000ad8c0d1fe7ccf848..3bc7a3781aa4c1dae51275af1240b1b63f7e9bcf 100644 (file)
@@ -7,20 +7,26 @@
 // (C) 2003, Cesar Octavio Lopez Nataren, <cesar@ciencias.unam.mx>
 //
 
+using System;
 using System.Text;
+using System.Reflection;
+using System.Reflection.Emit;
 
 namespace Microsoft.JScript {
 
        public class VariableDeclaration : Statement {
 
                private string id;
-               private string type;
+               private Type type;
                private AST val;
 
-               internal VariableDeclaration (string id, string type, AST init)
+               internal VariableDeclaration (string id, string t, AST init)
                {
                        this.id = id;
-                       this.type = type;
+
+                       if (t == null)
+                               this.type = typeof (System.Object);
+                       
                        this.val = init;
                }
 
@@ -31,7 +37,7 @@ namespace Microsoft.JScript {
                }
 
                
-               public string Type {
+               public Type Type {
                        get { return type; }
                        set { type = value; }
                }
@@ -43,9 +49,22 @@ namespace Microsoft.JScript {
 
                        sb.Append (Id);
                        sb.Append (" = ");
-                       sb.Append (val.ToString ());
+
+                       if (val != null)
+                               sb.Append (val.ToString ());
 
                        return sb.ToString ();
                }
+
+               internal override void Emit (EmitContext ec)
+               {
+                       FieldBuilder field;
+                       TypeBuilder type  = ec.type_builder;
+
+                       field = type.DefineField (id, Type,
+                                                 FieldAttributes.Public |
+                                                 FieldAttributes.Static);
+                                                 
+               }
        }
 }
index 8d0c10ac5305ccea3dac03accca4f8af2d716a7d..b7505aaee10ac642e4021446a9f0867db8f40db8 100644 (file)
@@ -37,5 +37,13 @@ namespace Microsoft.JScript {
 
                        return sb.ToString ();
                }
+
+               internal override void Emit (EmitContext ec)
+               {
+                       int i, size = var_decls.Count;
+
+                       for (i = 0; i < size; i++)
+                               ((VariableDeclaration) var_decls [i]).Emit (ec);
+               }
        }
-}
\ No newline at end of file
+}
index 3d4a550a2983fd4a2270b402cd4e159da946b9cb..c0f26e31e7c5253df9d1c7872a9ebf9159096fd3 100644 (file)
@@ -9,5 +9,9 @@
 namespace Microsoft.JScript {
 
        public abstract class AST {
+
+               internal virtual void Emit (EmitContext ec)
+               {
+               }
        }
 }
\ No newline at end of file
index 3fdcf81f57081b258c959bda43ae4caa041fedf4..8bc4cad3ecc14ea1fc6026d6f39eed1575229d93 100644 (file)
@@ -8,11 +8,6 @@
 //
 
 using System;
-using System.IO;
-using System.Collections;
-using System.Reflection.Emit;
-using System.Reflection;
-using System.Runtime.CompilerServices;
 
 namespace Microsoft.JScript {
 
@@ -32,6 +27,8 @@ namespace Microsoft.JScript {
                        ScriptBlock prog_tree = parser.Parse ();
 
                        Console.WriteLine (prog_tree.ToString ());
+
+                       CodeGenerator.Run (args [0], prog_tree);
                }
        }
-}
\ No newline at end of file
+}