Skip to content

loctvl842/static-checker

Folders and files

NameName
Last commit message
Last commit date

Latest commit

 

History

19 Commits
 
 
 
 
 
 
 
 
 
 

Repository files navigation

🚀 Usage

Go to src directory and run the following commands

python run.py gen
python run.py test CheckerSuite

This assignment include two main parts:

Support class

class ExprRet:
    def __init__(self, type, isInitialized=None):
        self.astType = type
        self.isInitialized = isInitialized

Support Methods

getASTName()

    ### `getASTName` function used to get name of AST object
    ## @param targetObj can be type of AttributeDecl, MethodDecl, VarDecl, ConstDecl, ClassDecl, FieldAccess, ArrayCell, CallExpr, ClassType
    def getASTName(self, targetObj) -> str:

searchClassByName()

    ### `searchClass` function used to find existed class
    def searchClassByName(self, name: str) -> ClassDecl:

getMemDeclType()

    ### `getMemDeclType` function used to get Type of AST member of class
    def getMemDeclType(self, memDecl: MemDecl) -> Type:

searchMemberOfClassByName()

    ### `searchMemberOfClassByName` search a member of other class in global scope
    def searchMemberOfClassByName(self, classDecl: ClassDecl, targetMemberName: str) -> MemDecl:

searchMemberByName()

    ### `searchMemberByName` search a member of current checking class
    def searchMemberByName(self, targetMemberName: str) -> MemDecl:

searchDeclByName()

    ### `searchVarDecl` function used to search a Decl through name
    def searchDeclByName(self, targetname: str, visibleScopeDecls: List[Decl]) -> StoreDecl:

checkIsKidOf()

    ### `checkIsKidOf` function used to check if an object is a child of another by query bottom down
    def checkIsKidOf(self, targetChildName: str, targetParentName: str) -> bool:

checkTypeMatch()

    ### `checkTypeMatch` function used to check if rhs has the same type to lhs or can be con be coerce to lhs
    def checkTypeMatch(self, lhsType: Type, rhsType: Type) -> bool:

Static Checker

visitAccess

    ## @param memDeclType MethodDecl | AttributeDecl
    def visitAccess(self, ast, visibleScopeDecls: List[Decl], memDeclType) -> StoreDecl:

this function is used by visitFieldAccess, visitCallExpr, visitCallStmt, visitAssign

this function return the member searched

  • check error Undeclared(errorKind, fieldname), IllegalMemberAccess(ast)

visitId

    def visitId(self, ast: Id, visibleScopeDecls: List[Decl]) -> Type:
  • check error Undeclared(Identifier(), ast.name) (this function only check this type of error because the id checked here is the id used in expr; id like classname or methodname have to be checked in its own function for example: visitClassDecl, visitMethodDecl, ... )

visitBinaryOp

    def visitBinaryOp(self, ast: BinaryOp, visibleScopeDecls: List[Decl]) -> Type:
  • check error TypeMisMatch(ast)

visitUnaryOp

    def visitUnaryOp(self, ast: UnaryOp, visibleScopeDecls: List[Decl]) -> Type:

visitCallExpr

    def visitCallExpr(self, ast: CallExpr, visibleScopeDecls: List[Decl]) -> Type:
  • check error in visitAccess(), TypeMismatchInExpression(ast)

visitNewExpr

    def visitNewExpr(self, ast: NewExpr, visibleScopeDecls: List[Decl]) -> ExprRet:
  • check error Undeclared(Class(), name), Undeclared(Method(), "<init>"), TypeMismatchInExpression(ast)

visitArrayCell

    def visitArrayCell(self, ast: ArrayCell, visibleScopeDecls: List[Decl]) -> ExprRet:
  • check error TypeMismatchInExpression(ast)

visitFieldAccess

    def visitFieldAccess(self, ast: FieldAccess, visibleScopeDecls: List[Decl]) -> ExprRet:
  • check error in visitAccess()

visitIntLiteral()

    def visitIntLiteral(
        self, ast: IntLiteral, visibleScopeDecls: List[Decl]
    ) -> ExprRet:

visitFloatLiteral()

    def visitFloatLiteral(
        self, ast: FloatLiteral, visibleScopeDecls: List[Decl]
    ) -> ExprRet:

visitStringLiteral()

    def visitStringLiteral(
        self, ast: StringLiteral, visibleScopeDecls: List[Decl]
    ) -> ExprRet:

visitBoolLiteral()

    def visitBooleanLiteral(
        self, ast: BooleanLiteral, visibleScopeDecls: List[Decl]
    ) -> ExprRet:

visitArrayLiteral

    def visitArrayLiteral(self, ast: ArrayLiteral, temp) -> ExprRet:
  • check error IllegalArrayLiteral(ast)

visitAssign

    def visitAssign(self, ast: Assign, visibleScopeDecls: List[StoreDecl]) -> None:
  • check error Undeclared(Identifier(), lhsName)
  • check error TypeMismatchInStatement(assignStmt)
  • check error CannotAssignToConstant(assignStmt) (check if lhs is connstant)

visitIf

    def visitIf(self, ast: If, visibleScopeDecls: List[StoreDecl]) -> None:
  • check error TypeMismatchInStatement(ast)

visitFor

    def visitFor(self, ast: For, visibleScopeDecls: List[StoreDecl]) -> None:
  • check error TypeMismatchInStatement(ast)

visitBreak

    def visitBreak(self, ast: Break, visibleScopeDecls: List[StoreDecl]) -> None:
  • check error MustInLoop(ast)

visitContinue

    def visitContinue(self, ast: Continue, visibleScopeDecls: List[StoreDecl]) -> None:
  • check error MustInLoop(ast)

visitReturn()

    def visitReturn(self, ast :Return, visibleScopeDecls: List[StoreDecl]) -> None:
  • check error TypeMismatchInStatement(ast)

visitCallStmt()

    def visitCallStmt(self, ast: CallStmt, visibleScopeDecls: List[StoreDecl]) -> None:
  • check error in visitAccess and TypeMismatchInStatement(ast)

visitVarDecl

    def visitVarDecl(self, ast: VarDecl, visibleScopeDecls: list[StoreDecl]) -> ExprRet:
  • check error TypeMismatchInStatement(Assign(ast.variable, ast.varInit))

visitBlock

    def visitBlock(self, ast: Block, visibleScopeDecls: List[Decl]) -> None:
  • check error Redeclared(errorKind, declName) (only check between declares in block)

visitConstDecl

    def visitConstDecl(self, ast: ConstDecl, visibleScopeDecls: List[Decl]) -> ExprRet:
  • check error TypeMismatchInConstant(ast), IllegalConstantExpression(ast.value)

visitClassDecl

    def visitClassDecl(self, ast: ClassDecl, globalScopeDecls: List[Decl]) -> ClassDecl:
  • check error Redeclared(Class(), classname) the new class
  • check error Undeclared(Class(), parentname) the parent of new class

visitMethodDecl

    def visitMethodDecl(self, ast: MethodDecl, classScopeDecls: List[Decl]) -> MethodDecl:
  • check error Redeclared(Method(), methodName) of the new method
  • check error Redeclared(Parameter(),paramName) in list of params
  • check error Redeclared(StoreDecl, name) in list of decls of Block (only if StoreDecl exist in list of parameters)

visitAttributeDecl

    def visitAttributeDecl(self, ast: AttributeDecl, classScopeDecls: List[MemDecl]) -> AttributeDecl:
  • check error Redeclared(Attribute(), attributeName)

visitProgram

    def visitProgram(self, ast: Program, c) -> None:
  • add one existed class io to the completely new program
  • create globalScopeDecls store in global

About

BKOOL language static-checker

Topics

Resources

Stars

Watchers

Forks

Releases

No releases published

Packages

No packages published