Add initial typechecker for AST #2
102
src/Typecheck.hs
102
src/Typecheck.hs
@ -78,6 +78,22 @@ typeCheckExpression (BinaryOperation op expr1 expr2) symtab classes =
|
|||||||
Or -> checkLogicalOperation op expr1' expr2' type1 type2
|
Or -> checkLogicalOperation op expr1' expr2' type1 type2
|
||||||
NameResolution -> resolveNameResolution expr1' expr2 symtab classes
|
NameResolution -> resolveNameResolution expr1' expr2 symtab classes
|
||||||
|
|
||||||
|
typeCheckExpression (UnaryOperation op expr) symtab classes =
|
||||||
|
let expr' = typeCheckExpression expr symtab classes
|
||||||
|
type' = getTypeFromExpr expr'
|
||||||
|
in case op of
|
||||||
|
Not ->
|
||||||
|
if type' == "boolean"
|
||||||
|
then
|
||||||
|
TypedExpression "boolean" (UnaryOperation op expr')
|
||||||
|
else
|
||||||
|
error "Logical NOT operation requires an operand of type boolean"
|
||||||
|
Minus ->
|
||||||
|
if type' == "int" || type' == "char"
|
||||||
|
then
|
||||||
|
TypedExpression type' (UnaryOperation op expr')
|
||||||
|
else
|
||||||
|
error "Unary minus operation requires an operand of type int or char"
|
||||||
|
|
||||||
typeCheckExpression (StatementExpressionExpression stmtExpr) symtab classes =
|
typeCheckExpression (StatementExpressionExpression stmtExpr) symtab classes =
|
||||||
let stmtExpr' = typeCheckStatementExpression stmtExpr symtab classes
|
let stmtExpr' = typeCheckStatementExpression stmtExpr symtab classes
|
||||||
@ -147,61 +163,41 @@ typeCheckStatementExpression (MethodCall expr methodName args) symtab classes =
|
|||||||
Nothing -> error $ "Class for object type '" ++ objType ++ "' not found."
|
Nothing -> error $ "Class for object type '" ++ objType ++ "' not found."
|
||||||
_ -> error "Invalid object type for method call. Object must have a class type."
|
_ -> error "Invalid object type for method call. Object must have a class type."
|
||||||
|
|
||||||
typeCheckStatementExpression (UnaryOperation op expr) symtab classes =
|
typeCheckStatementExpression (PostIncrement expr) symtab classes =
|
||||||
let expr' = typeCheckExpression expr symtab classes
|
let expr' = typeCheckExpression expr symtab classes
|
||||||
type' = getTypeFromExpr expr'
|
type' = getTypeFromExpr expr'
|
||||||
in case op of
|
in if type' == "int" || type' == "char"
|
||||||
Not ->
|
then
|
||||||
if type' == "boolean"
|
TypedStatementExpression type' (PostIncrement expr')
|
||||||
then
|
else
|
||||||
TypedStatementExpression "boolean" (UnaryOperation op expr')
|
error "Post-increment operation requires an operand of type int or char"
|
||||||
else
|
|
||||||
error "Logical NOT operation requires an operand of type boolean"
|
typeCheckStatementExpression (PostDecrement expr) symtab classes =
|
||||||
Minus ->
|
let expr' = typeCheckExpression expr symtab classes
|
||||||
if type' == "int"
|
type' = getTypeFromExpr expr'
|
||||||
then
|
in if type' == "int" || type' == "char"
|
||||||
TypedStatementExpression "int" (UnaryOperation op expr')
|
then
|
||||||
else if type' == "char"
|
TypedStatementExpression type' (PostDecrement expr')
|
||||||
then
|
else
|
||||||
TypedStatementExpression "char" (UnaryOperation op expr')
|
error "Post-decrement operation requires an operand of type int or char"
|
||||||
else
|
|
||||||
error "Unary minus operation requires an operand of type int or char"
|
typeCheckStatementExpression (PreIncrement expr) symtab classes =
|
||||||
PostIncrement ->
|
let expr' = typeCheckExpression expr symtab classes
|
||||||
if type' == "int"
|
type' = getTypeFromExpr expr'
|
||||||
then
|
in if type' == "int" || type' == "char"
|
||||||
TypedStatementExpression "int" (UnaryOperation op expr')
|
then
|
||||||
else if type' == "char"
|
TypedStatementExpression type' (PreIncrement expr')
|
||||||
then
|
else
|
||||||
TypedStatementExpression "char" (UnaryOperation op expr')
|
error "Pre-increment operation requires an operand of type int or char"
|
||||||
else
|
|
||||||
error "Post-increment operation requires an operand of type int or char"
|
typeCheckStatementExpression (PreDecrement expr) symtab classes =
|
||||||
PostDecrement ->
|
let expr' = typeCheckExpression expr symtab classes
|
||||||
if type' == "int"
|
type' = getTypeFromExpr expr'
|
||||||
then
|
in if type' == "int" || type' == "char"
|
||||||
TypedStatementExpression "int" (UnaryOperation op expr')
|
then
|
||||||
else if type' == "char"
|
TypedStatementExpression type' (PreDecrement expr')
|
||||||
then
|
else
|
||||||
TypedStatementExpression "char" (UnaryOperation op expr')
|
error "Pre-decrement operation requires an operand of type int or char"
|
||||||
else
|
|
||||||
error "Post-decrement operation requires an operand of type int or char"
|
|
||||||
PreIncrement ->
|
|
||||||
if type' == "int"
|
|
||||||
then
|
|
||||||
TypedStatementExpression "int" (UnaryOperation op expr')
|
|
||||||
else if type' == "char"
|
|
||||||
then
|
|
||||||
TypedStatementExpression "char" (UnaryOperation op expr')
|
|
||||||
else
|
|
||||||
error "Pre-increment operation requires an operand of type int or char"
|
|
||||||
PreDecrement ->
|
|
||||||
if type' == "int"
|
|
||||||
then
|
|
||||||
TypedStatementExpression "int" (UnaryOperation op expr')
|
|
||||||
else if type' == "char"
|
|
||||||
then
|
|
||||||
TypedStatementExpression "char" (UnaryOperation op expr')
|
|
||||||
else
|
|
||||||
error "Pre-decrement operation requires an operand of type int or char"
|
|
||||||
|
|
||||||
-- ********************************** Type Checking: Statements **********************************
|
-- ********************************** Type Checking: Statements **********************************
|
||||||
|
|
||||||
|
Loading…
Reference in New Issue
Block a user