Advertisement
Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- class StaticCheck(Visitor):
- def visitProgram(self,ctx:Program,o:object):
- for decl in ctx.decl:
- self.visit(decl,o)
- def visitClassDecl(self,ctx:ClassDecl,o:object):
- o=[]
- for mem in ctx.mem:
- self.visit(mem,o)
- def visitVarDecl(self,ctx:VarDecl,o:object):
- if ctx.name in o:
- raise RedeclaredField(ctx.name)
- o+=[ctx.name]
- def visitFuncDecl(self,ctx:FuncDecl,o:object):
- if ctx.name in o:
- raise RedeclaredMethod(ctx.name)
- o+=[ctx.name]
- def visitIntType(self,ctx:IntType,o:object):pass
- def visitFloatType(self,ctx:FloatType,o:object):pass
- def visitClassType(self,ctx:ClassType,o:object):pass
- def visitIntLit(self,ctx:IntLit,o:object):pass
- def visitId(self,ctx:Id,o:object):pass
- def visitFieldAccess(self,ctx:FieldAccess,o:object):pass
- ##################################
- class GetEnv(Visitor):
- def visitProgram(self,ctx:Program,o:object):
- o = []
- for decl in ctx.decl:
- self.visit(decl, o)
- return o
- def visitClassDecl(self,ctx:ClassDecl,o:object):
- env = []
- for mem in ctx.mem:
- self.visit(mem, env)
- o += [(ctx.name, ctx.parent, env)]
- def visitVarDecl(self,ctx:VarDecl,o:object):
- if ctx.name in o:
- raise RedeclaredField(ctx.name)
- o += [(ctx.name, ctx.typ)]
- def visitFuncDecl(self,ctx:FuncDecl,o:object):
- if ctx.name in o:
- raise RedeclaredMethod(ctx.name)
- o += [(ctx.name, None)]
- class StaticCheck(Visitor):
- def visitProgram(self,ctx:Program,o:object):
- env = GetEnv().visit(ctx, o)
- # print(env)
- for decl in ctx.decl:
- self.visit(decl, env)
- def visitClassDecl(self,ctx:ClassDecl,o:object):
- for mem in ctx.mem:
- if type(mem) is FuncDecl:
- self.visit(mem, o)
- def visitFuncDecl(self,ctx:FuncDecl,o:object):
- local = ctx.param + ctx.body[0]
- listOfClass = o
- for expr in ctx.body[1]:
- self.visit(expr, (listOfClass, local))
- def visitId(self,ctx:Id,o:object):
- typ = None
- for x in o[1]:
- if x.name == ctx.name:
- typ = x.typ
- if not typ:
- raise UndeclaredIdentifier(ctx.name)
- return typ
- def visitFieldAccess(self,ctx:FieldAccess,o:object):
- typ = self.visit(ctx.exp, o)
- if type(typ) is ClassType:
- c = None
- for x in o[0]:
- if typ.name == x[0]:
- c = x
- if not c: raise UndeclaredClass(typ.name)
- for mem in c[2]:
- if mem[0] == ctx.field:
- return
- raise UndeclaredField(ctx.field)
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement