diff --git a/sources/zweic/Analyzer.scala b/sources/zweic/Analyzer.scala index 741106d..7a3001d 100755 --- a/sources/zweic/Analyzer.scala +++ b/sources/zweic/Analyzer.scala @@ -36,7 +36,7 @@ case ClassDef(name, None, members) => classScope.get(name.name) match { case Some(c) => - Report.error(tree.pos, "Class already defined: " + name.name) + Report.error(tree.pos, "Class already defined: " + name) case None => val cs = ClassSymbol(tree.pos, name.name, None); classScope(name.name) = cs; @@ -45,7 +45,7 @@ case ClassDef(name, extend, members) => classScope.get(name.name) match { case Some(c) => - Report.error(tree.pos, "Class already defined: " + name.name); + Report.error(tree.pos, "Class already defined: " + name); case None => val cs = ClassSymbol(tree.pos, name.name, classScope.get(extend.get.name)); classScope(name.name) = cs; @@ -58,16 +58,34 @@ private def analyzeMember(ownerClass: ClassSymbol, tree: Member): Unit = tree.match { case FieldDecl(Formal(name, typ)) => - // TODO check that field does not yet exist! - ownerClass.enterField(FieldSymbol(tree.pos, name.name, analyzeType(typ))) + ownerClass.lookupField(name.name) match { + case Some(v) => + Report.error(tree.pos, "Class variable already defined: " + name); + case None => + name.sym= FieldSymbol(tree.pos, name.name, analyzeType(typ)); + ownerClass.enterField(name.sym.asInstanceOf[FieldSymbol]); + } case MethodDef(name, args, rtype, expr) => + var myVarScope = emptyVarScope; + + for ( val x <- ownerClass.allFields ) myVarScope = myVarScope + x.name -> x.asInstanceOf[VarSymbol]; + + val paramtypes = for ( val f <- args ) yield { + //TODO: check that there isn't already a class field with the same name + f.name.sym = VarSymbol(f.pos, f.name.name, analyzeType(f.typ)); + myVarScope = myVarScope + f.name.name -> f.name.sym.asInstanceOf[VarSymbol]; + analyzeType(f.typ); + } + + val rt = analyzeType(rtype); + checkSubtype(tree.pos, "Return type mismatch", analyzeExpr(myVarScope, expr), rt); + name.sym = MethodSymbol(tree.pos, name.name, paramtypes, rt); + ownerClass.lookupMethod(name.name) match { case Some(m) => - var paramtypes = for ( val Formal(x,y) <- args ) yield analyzeType(y); - ownerClass.enterMethod(MethodSymbol(tree.pos, name.name, paramtypes, analyzeType(rtype))) + ownerClass.enterMethod(name.sym.asInstanceOf[MethodSymbol]); case None => - var paramtypes = for ( val Formal(x,y) <- args ) yield analyzeType(y); - ownerClass.enterNewMethod(MethodSymbol(tree.pos, name.name, paramtypes, analyzeType(rtype))) + ownerClass.enterNewMethod(name.sym.asInstanceOf[MethodSymbol]); } } @@ -88,9 +106,8 @@ case None => val mt = analyzeType(typ); checkSubtype(tree.pos, "Incompatible types", analyzeExpr(varScope, expr), mt); - val ms = VarSymbol(tree.pos, name.name, mt); - name.sym = ms; - varScope + name.name -> ms; + name.sym = VarSymbol(tree.pos, name.name, mt); + varScope + name.name -> name.sym.asInstanceOf[VarSymbol]; } case Set(ident, expr) =>