changeset 94:48bb2287c035 new_gen

Added Modules. Right now it's very simple - will grow with time and need.
author Anders Johnsen <skabet@gmail.com>
date Tue, 06 May 2008 16:24:14 +0200
parents 621cedba53ea
children 6aecbe5a7706
files basic/SourceManager.d dang/compiler.d gen/CodeGen.d lexer/Keyword.d lexer/Token.d parser/Action.d parser/Parser.d sema/AstAction.d sema/ScopeBuilder.d sema/Visitor.d tools/AstPrinter.d tools/DotPrinter.d
diffstat 12 files changed, 134 insertions(+), 56 deletions(-) [+]
line wrap: on
line diff
--- a/basic/SourceManager.d	Mon May 05 20:53:13 2008 +0200
+++ b/basic/SourceManager.d	Tue May 06 16:24:14 2008 +0200
@@ -146,6 +146,14 @@
             getFileOffset(loc.end));
     }
 
+    /**
+      Get the file name of a loc.
+     **/
+    string getFile(SourceLocation loc)
+    {
+        return checkpoints[loc.fileID].filename;
+    }
+
 private:
     synchronized
         SourceLocation createCheckpoints(string data, string source_file)
--- a/dang/compiler.d	Mon May 05 20:53:13 2008 +0200
+++ b/dang/compiler.d	Tue May 06 16:24:14 2008 +0200
@@ -15,7 +15,7 @@
 
 import basic.Message;
 
-import ast.Decl;
+import ast.Module;
 
 import tools.AstPrinter,
        tools.DotPrinter;
@@ -82,7 +82,7 @@
     Signal!(Lexer) postLex;
 
     Signal!(Lexer) preParse;
-    Signal!(Decl[], SourceManager) postParse;
+    Signal!(Module, SourceManager) postParse;
 
     preStart.attach(&checkFiles);
 
@@ -140,36 +140,36 @@
     auto what = options["what-to-do"];
     if (what == "" || what == "gen-llvm")
         postParse.attach(
-            (Decl[] decls, SourceManager sm) {
+            (Module m, SourceManager sm) {
                 StopWatch w; w.start;
                 auto llvmGen = new CodeGen();
                 auto file = new FileConduit("out.bc", FileConduit.WriteCreate);
-                llvmGen.gen(decls, file.fileHandle, optimize, inline);
+                llvmGen.gen(m, file.fileHandle, optimize, inline);
                 timings ~= Measurement("Generating LLVM bytecode", w.stop);
             });
     else if (what == "compile")
         postParse.attach(
-            (Decl[] decls, SourceManager sm) {
+            (Module m, SourceManager sm) {
                 StopWatch w; w.start;
                 auto llvmGen = new CodeGen();
                 auto llc = new Process("llc");
-                llvmGen.gen(decls, llc.stdin.fileHandle, optimize, inline);
+                llvmGen.gen(m, llc.stdin.fileHandle, optimize, inline);
                 timings ~= Measurement("Generating assemble bytecode", w.stop);
             });
     else if (what == "dot")
         postParse.attach(
-            (Decl[] decls, SourceManager sm) {
+            (Module m, SourceManager sm) {
                 StopWatch w; w.start;
                 auto print = new DotPrinter();
-                print.print(decls);
+                print.print(m);
                 timings ~= Measurement("Generating dot output", w.stop);
             });
     else if (what == "code")
         postParse.attach(
-            (Decl[] decls, SourceManager sm) {
+            (Module m, SourceManager sm) {
                 StopWatch w; w.start;
                 auto print = new AstPrinter(sm);
-                print.print(decls);
+                print.print(m);
                 timings ~= Measurement("Converting AST to text", w.stop);
             });
     StopWatch total;
@@ -188,24 +188,24 @@
         watch.start;
         auto parser = new Parser(messages);
         auto action = new AstAction(src_mgr);
-        auto decls = cast(Decl[])parser.parse(src_mgr, lexer, action);
+        auto m = cast(Module)parser.parse(src_mgr, lexer, action);
         timings ~= Measurement("Lex + Parse", watch.stop);
         messages.checkErrors(ExitLevel.Parser);
 
         StopWatch watch2;
         watch.start;
         watch2.start;
-        (new ScopeBuilder).visit(decls);
+        (new ScopeBuilder).visit(m);
         auto scope_builder = watch2.stop;
         watch2.start;
-        (new ScopeCheck).visit(decls);
+        (new ScopeCheck).visit(m);
         auto scope_check = watch2.stop;
         watch2.start;
-        (new TypeCheck).visit(decls);
+        (new TypeCheck).visit(m);
         auto type_check = watch2.stop;
         watch2.start;
 
-        foreach (decl; decls)
+        foreach (decl; m.decls)
             decl.simplify();
         auto simplify = watch2.stop;
         auto extra_stuff = watch.stop;
@@ -214,7 +214,7 @@
         timings ~= Measurement("  - Checking scopes", scope_check);
         timings ~= Measurement("  - Checking types", type_check);
 
-        postParse(decls, src_mgr);
+        postParse(m, src_mgr);
     }
     timings ~= Measurement("Total", total.stop);
 
--- a/gen/CodeGen.d	Mon May 05 20:53:13 2008 +0200
+++ b/gen/CodeGen.d	Tue May 06 16:24:14 2008 +0200
@@ -4,9 +4,10 @@
        Int = tango.text.convert.Integer;
 import tango.core.Array : find, partition;
 
-import llvm.llvm;
+import LLVM = llvm.llvm;
 
-import ast.Decl,
+import ast.Module,
+       ast.Decl,
        ast.Stmt,
        ast.Exp;
 
@@ -18,6 +19,20 @@
 import sema.Scope,
        sema.Visitor;
 
+alias LLVM.Value Value;
+alias LLVM.Type Type;
+alias LLVM.Function Function;
+alias LLVM.PointerType PointerType;
+alias LLVM.FunctionType FunctionType;
+alias LLVM.IntPredicate IntPredicate;
+alias LLVM.ParamAttr ParamAttr;
+alias LLVM.ConstantInt ConstantInt;
+alias LLVM.GlobalVariable GlobalVariable;
+alias LLVM.IntegerType IntegerType;
+alias LLVM.BasicBlock BasicBlock;
+alias LLVM.StructType StructType;
+alias LLVM.ArrayType ArrayType;
+
 private char[] genBuildCmp(char[] p)
 {
     return `
@@ -41,7 +56,7 @@
     this()
     {
         alias BinaryExp.Operator op;
-        b = new Builder;
+        b = new LLVM.Builder;
         
         opToLLVM = [
             op.Add      : &b.buildAdd,
@@ -65,10 +80,10 @@
         b.dispose();
     }
 
-    void gen(Decl[] decls, uint handle, bool optimize, bool inline)
+    void gen(Module mod, uint handle, bool optimize, bool inline)
     {
         // create module
-        m = new Module("main_module");
+        m = new LLVM.Module("main_module");
         scope(exit) m.dispose();
 
         table.enterScope;
@@ -124,14 +139,14 @@
                 }
             };
         auto visitor = new VisitFuncDecls(registerFunc);
-        visitor.visit(decls);
+        visitor.visit(mod);
         // Before beginning we move all top level var-decls to the start
         // and then we generate the var-decls first
         // partition is NOT required to be stable, but that should not create
         // any problems.
-        partition(decls, (Decl d) { return d.declType == DeclType.VarDecl; });
+        partition(mod.decls, (Decl d) { return d.declType == DeclType.VarDecl; });
 
-        foreach (decl; decls)
+        foreach (decl; mod.decls)
             genRootDecl(decl);
 
         table.leaveScope;
@@ -738,8 +753,8 @@
 private:
 
     // llvm stuff
-    Module m;
-    Builder b;
+    LLVM.Module m;
+    LLVM.Builder b;
     Function llvm_memcpy;
     Type BytePtr;
     Type[DType] type_map;
@@ -759,9 +774,9 @@
         this.dg = dg;
     }
 
-    override void visit(Decl[] decls)
+    override void visitModule(Module m)
     {
-        foreach (decl; decls)
+        foreach (decl; m.decls)
             if (auto f = cast(FuncDecl)decl)
                 dg(f);
     }
--- a/lexer/Keyword.d	Mon May 05 20:53:13 2008 +0200
+++ b/lexer/Keyword.d	Tue May 06 16:24:14 2008 +0200
@@ -40,6 +40,10 @@
         "case"      : Tok.Case,
         "default"   : Tok.Default,
         "return"    : Tok.Return,
-        "cast"      : Tok.Cast
+        "cast"      : Tok.Cast,
+
+        // modules
+        "module"    : Tok.Module,
+        "import"    : Tok.Import
     ];
 }
--- a/lexer/Token.d	Mon May 05 20:53:13 2008 +0200
+++ b/lexer/Token.d	Tue May 06 16:24:14 2008 +0200
@@ -134,6 +134,8 @@
     Switch, Case, Default,
     Return, Cast,
 
+    Module, Import,
+
 }
 
 /**
@@ -185,6 +187,8 @@
         Tok.Struct:"Struct",
         Tok.Colon:"Colon",
         Tok.Seperator:"Seperator",
-        Tok.Cast:"Cast"
+        Tok.Cast:"Cast",
+        Tok.Module:"Module",
+        Tok.Import:"Import"
     ];
 }
--- a/parser/Action.d	Mon May 05 20:53:13 2008 +0200
+++ b/parser/Action.d	Tue May 06 16:24:14 2008 +0200
@@ -78,6 +78,18 @@
     alias Object ExprT;
     alias Object StmtT; /// ditto
     alias Object DeclT; /// ditto
+    alias Object ModuleT; /// ditto
+
+    // -- Modules --
+
+    ModuleT actOnModule(char[] name)
+    {
+        return null;
+    }
+
+    void actOnModuleDecl(ModuleT m, DeclT d)
+    {
+    }
 
     // -- Declarations --
 
--- a/parser/Parser.d	Mon May 05 20:53:13 2008 +0200
+++ b/parser/Parser.d	Tue May 06 16:24:14 2008 +0200
@@ -20,6 +20,7 @@
     alias Object Exp;
     alias Object Stmt;
     alias Object Decl;
+    alias Object Module;
 
 public:
 
@@ -28,18 +29,37 @@
         this.messages = messages;
     }
 
-    Decl[] parse(SourceManager sm, Lexer lexer, Action act)
+    Module parse(SourceManager sm, Lexer lexer, Action act)
     {
         this.sm = sm;
         this.lexer = lexer;
         this.action = act;
 
-        Decl[] declarations;
+        auto m = parseModule();
 
         while(lexer.peek.type != Tok.EOF)
-            declarations ~= parseDecl();
+            action.actOnModuleDecl(m, parseDecl());
+
+        return m;
+    }
 
-        return declarations;
+    Module parseModule()
+    {
+        if(lexer.peek.type == Tok.Module)
+        {
+            lexer.next;
+            if(lexer.peek.type != Tok.Identifier)
+                messages.report(UnexpectedTok, lexer.peek.location)
+                    .arg(lexer.peek.type)
+                    .arg(Tok.Identifier)
+                    .fatal(ExitLevel.Parser);
+    
+            auto m = action.actOnModule(sm.getText(lexer.next.asRange));
+            require(Tok.Seperator);
+            return m;
+        }
+
+        return action.actOnModule(sm.getFile(lexer.peek.location));
     }
 
     Decl parseDecl()
--- a/sema/AstAction.d	Mon May 05 20:53:13 2008 +0200
+++ b/sema/AstAction.d	Tue May 06 16:24:14 2008 +0200
@@ -7,7 +7,8 @@
 import misc.Error,
        basic.SourceManager;
 
-import ast.Exp,
+import ast.Module,
+       ast.Exp,
        ast.Stmt,
        ast.Decl;
 
@@ -41,6 +42,15 @@
         return new Identifier(t.location, sm.getText(t.asRange));
     }
 
+    override ModuleT actOnModule(char[] name)
+    {
+        return new Module(name);
+    }
+
+    override void actOnModuleDecl(ModuleT m, DeclT d)
+    {
+        (cast(Module)m).addDecl(cast(Decl)d);
+    }
 
     // -- Declarations --
     override DeclT actOnDeclarator(ref Id type, ref Id id, ExprT init)
--- a/sema/ScopeBuilder.d	Mon May 05 20:53:13 2008 +0200
+++ b/sema/ScopeBuilder.d	Tue May 06 16:24:14 2008 +0200
@@ -11,12 +11,6 @@
 
 class ForwardReference : Visitor!(void)
 {
-    override void visit(Decl[] decls)
-    {
-        foreach (decl; decls)
-            visitDecl(decl);
-    }
-
     override void visitFuncDecl(FuncDecl d)
     {
         visitExp(d.returnType);
@@ -78,12 +72,11 @@
         table[0].types["ulong"]   = DType.ULong;
     }
 
-    override void visit(Decl[] decls)
+    override void visit(Module m)
     {
-        foreach (decl; decls)
-            visitDecl(decl);
+        visitModule(m);
         auto fr = new ForwardReference();
-        fr.visit(decls);
+        fr.visit(m);
     }
 
     override void visitDecl(Decl d)
--- a/sema/Visitor.d	Mon May 05 20:53:13 2008 +0200
+++ b/sema/Visitor.d	Tue May 06 16:24:14 2008 +0200
@@ -3,25 +3,35 @@
 import tango.io.Stdout;
 
 public
-import ast.Decl,
+import ast.Module,
+       ast.Decl,
        ast.Stmt,
        ast.Exp;
 
 import lexer.Token;
 
-class Visitor(FinalT = int, DeclT = FinalT, StmtT = DeclT, ExpT = StmtT)
+class Visitor(FinalT = int, ModuleT = FinalT, DeclT = ModuleT, StmtT = DeclT, ExpT = StmtT)
 {
 public:
-    FinalT visit(Decl[] decls)
+    FinalT visit(Module m)
     {
-        foreach (decl; decls)
-            visitDecl(decl);
+        visitModule(m);
         static if (is(FinalT == void))
             return;
         else
             return FinalT.init;
     }
 
+    ModuleT visitModule(Module m)
+    {
+        foreach (decl; m.decls)
+            visitDecl(decl);
+        static if (is(ModuleT == void))
+            return;
+        else
+            return ModuleT.init;
+    }
+
     DeclT visitDecl(Decl decl)
     {
         switch(decl.declType)
--- a/tools/AstPrinter.d	Mon May 05 20:53:13 2008 +0200
+++ b/tools/AstPrinter.d	Tue May 06 16:24:14 2008 +0200
@@ -2,7 +2,8 @@
 
 import tango.io.Stdout;
 
-import ast.Decl,
+import ast.Module,
+       ast.Decl,
        ast.Stmt,
        ast.Exp;
 
@@ -18,9 +19,9 @@
         this.sm = sm;
     }
 
-    void print(Decl[] decls)
+    void print(Module m)
     {
-        foreach(decl ; decls)
+        foreach(decl ; m.decls)
         {
             printDecl(decl);
         }
--- a/tools/DotPrinter.d	Mon May 05 20:53:13 2008 +0200
+++ b/tools/DotPrinter.d	Tue May 06 16:24:14 2008 +0200
@@ -3,7 +3,8 @@
 import tango.io.Stdout,
        Int = tango.text.convert.Integer;
 
-import ast.Decl,
+import ast.Module,
+       ast.Decl,
        ast.Stmt,
        ast.Exp;
 
@@ -16,10 +17,10 @@
     private char[][void*] identifiers;
     private int current_id = 0;
 
-    void print(Decl[] decls)
+    void print(Module m)
     {
         Stdout("digraph {").newline;
-        foreach(decl ; decls)
+        foreach(decl ; m.decls)
         {
             printDecl(decl);
         }