added type to sem.icl =/=
[cc1516.git] / sem.icl
diff --git a/sem.icl b/sem.icl
index a041cee..66d9024 100644 (file)
--- a/sem.icl
+++ b/sem.icl
@@ -18,6 +18,7 @@ import StdString
 import StdTuple
 import StdList
 import StdBool
+import GenEq
 
 from Text import class Text(concat), instance Text String
 
@@ -32,7 +33,7 @@ from parse import :: ParserOutput, :: Error
 instance MonadTrans (StateT Gamma) where
     liftT m = StateT \s-> m >>= \a-> return (a, s)
 
-get = gets id
+get :== gets id
 
 sem :: AST -> SemOutput
 sem (AST vd fd) = case runStateT m ('Map'.newMap, getRandomStream 1) of
@@ -54,15 +55,21 @@ semFunDecl fd=:(FunDecl p f args mt vds stmts) =
        matchFunctions args ft >>= \tres->
     mapM semVarDecl vds >>= \newvds->
     mapM (checkStmt tres) stmts >>= \newstmts->
-       pure IntType >>= \returntype->
        case mt of
-               Nothing = reconstructType args returntype 
-               >>= \ftype->restoreGamma gamma 
+               Nothing = inferReturnType stmts
+                       >>= \returntype->reconstructType args returntype 
+                       >>= \ftype->restoreGamma gamma 
                        >>| putIdent f ftype >>| pure (
                        FunDecl p f args (Just ftype) newvds newstmts) 
                Just t = restoreGamma gamma 
                        >>| pure (FunDecl p f args mt newvds newstmts) 
 
+inferReturnType :: [Stmt] -> Env Type
+inferReturnType [] = pure VoidType
+inferReturnType [ReturnStmt (Just t):rest] = typeExpr t
+inferReturnType [ReturnStmt _:rest] = pure VoidType
+inferReturnType [_:rest] = inferReturnType rest
+
 reconstructType :: [String] Type -> Env Type
 reconstructType [] t = pure t
 reconstructType [x:xs] t = gets (\(st, r)->'Map'.get x st)
@@ -126,7 +133,6 @@ typeExpr (VarExpr p (VarDef ident fs)) = gets (\(st, r)->'Map'.get ident st)
     >>= \mt->case mt of
         Nothing = liftT $ Left $ UndeclaredVariableError p ident
         Just t = unify t fs
-
 typeOp2 :: Expr Expr Op2 [Type] Type -> Env Type
 typeOp2 e1 e2 op ts ret = typeExpr e1 >>= \t1-> typeExpr e2 >>= \t2->
     unify t1 t2 >>= \t3->if (isMember t3 ts) (pure ret)
@@ -271,3 +277,8 @@ saveGamma = get
 
 restoreGamma :: Gamma -> Env Void
 restoreGamma (oldstate, _) = gets snd >>= \newr->put (oldstate, newr)
+
+derive gEq Type
+instance == Type where 
+       (==) (IdType _) (IdType _) = True
+       (==) o1 o2 = gEq{|*|} o1 o2