Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Features/void methods #86

Merged
merged 2 commits into from
Feb 13, 2015
Merged
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
25 changes: 19 additions & 6 deletions src/types/Typechecker/Typechecker.hs
Original file line number Diff line number Diff line change
Expand Up @@ -119,7 +119,10 @@ instance Checkable Function where
do let typeParams = nub $ filter isTypeVar $ concatMap (typeComponents . ptype) funparams
ty <- local (addTypeParameters typeParams) $ checkType funtype
eParams <- mapM (\p -> local (addTypeParameters typeParams) $ typecheckParam p) funparams
eBody <- local (addParams eParams) $ pushHasType funbody ty
eBody <- local (addParams eParams) $
if isVoidType ty
then pushTypecheck funbody
else pushHasType funbody ty
return $ setType ty f {funtype = ty, funbody = eBody, funparams = eParams}
where
typecheckParam = (\p@(Param{ptype}) -> local (pushBT p) $
Expand Down Expand Up @@ -188,7 +191,10 @@ instance Checkable MethodDecl where
Just thisType <- asks $ varLookup thisName
when (isMainType thisType && mname == Name "main") checkMainParams
eMparams <- mapM (\p -> local (addTypeParameters typeParams) $ typecheckParam p) mparams
eBody <- local (addParams eMparams) $ pushHasType mbody ty
eBody <- local (addParams eMparams) $
if isVoidType ty
then pushTypecheck mbody
else pushHasType mbody ty
return $ setType ty m {mtype = ty, mbody = eBody, mparams = eMparams}
where
checkMainParams = unless ((map ptype mparams) `elem` [[] {-, [intType, arrayType stringType]-}]) $
Expand Down Expand Up @@ -718,7 +724,8 @@ instance Checkable Expr where
eOperand <- pushTypecheck operand
let eType = AST.getType eOperand
unless (isBoolType eType) $
tcError $ "Operator '" ++ show op ++ "' is only defined for boolean types"
tcError $ "Operator '" ++ show op ++ "' is only defined for boolean types\n" ++
"Expression '" ++ (show $ ppExpr eOperand) ++ "' has type '" ++ show eType ++ "'"
return $ setType boolType unary { operand = eOperand }

-- op \in {and, or}
Expand All @@ -743,15 +750,19 @@ instance Checkable Expr where
let lType = AST.getType eLoper
rType = AST.getType eRoper
unless (isBoolType lType && isBoolType rType) $
tcError $ "Operator '"++ show op ++ "' is only defined for boolean types"
tcError $ "Operator '"++ show op ++ "' is only defined for boolean types\n" ++
" Left type: '" ++ (show $ lType) ++ "'\n" ++
" Right type: '" ++ (show $ rType) ++ "'"
return $ setType boolType binop {loper = eLoper, roper = eRoper}
| op `elem` cmpOps =
do eLoper <- pushTypecheck loper
eRoper <- pushTypecheck roper
let lType = AST.getType eLoper
rType = AST.getType eRoper
unless (isNumeric lType && isNumeric rType) $
tcError $ "Operator "++ show op ++ " is only defined for numeric types"
tcError $ "Operator '"++ show op ++ "' is only defined for numeric types\n" ++
" Left type: '" ++ (show $ lType) ++ "'\n" ++
" Right type: '" ++ (show $ rType) ++ "'"
return $ setType boolType binop {loper = eLoper, roper = eRoper}
| op `elem` eqOps =
do eLoper <- pushTypecheck loper
Expand All @@ -763,7 +774,9 @@ instance Checkable Expr where
let lType = AST.getType eLoper
rType = AST.getType eRoper
unless (isNumeric lType && isNumeric rType) $
tcError $ "Operator "++ show op ++ " is only defined for numeric types"
tcError $ "Operator '"++ show op ++ "' is only defined for numeric types\n" ++
" Left type: '" ++ (show $ lType) ++ "'\n" ++
" Right type: '" ++ (show $ rType) ++ "'"
return $ setType (coerceTypes lType rType) binop {loper = eLoper, roper = eRoper}
| otherwise = tcError $ "Undefined binary operator '" ++ show op ++ "'"
where
Expand Down