diff --git a/sources/zweic/Symbol.scala b/sources/zweic/Symbol.scala new file mode 100755 index 0000000..796dd95 --- /dev/null +++ b/sources/zweic/Symbol.scala @@ -0,0 +1,102 @@ +/* zweic -- a compiler for zwei + * + * Stephane Micheloud & LAMP + * + * $Id$ + */ + +package zweic; + +import scala.collection.immutable.{Map, ListMap}; + +/** + * This class provides a representation for symbol table entries. + */ +abstract class Symbol { + + def pos: Int; + + def name: String; + + /** + * Offset of the symbol. For variables, that's the offset + * relative to the frame pointer; for functions that's the PC of + * the first instruction. + */ + var offset: Int = -1; + +} + +case class ClassSymbol(pos: Int, name: String, superclass: Option[ClassSymbol]) + extends Symbol +{ + private var fields: Map[String,FieldSymbol] = + superclass match { + case None => ListMap.Empty[String,FieldSymbol] + case Some(s) => s.fields + } + + private var methods: Map[String,MethodSymbol] = + superclass match { + case None => ListMap.Empty[String,MethodSymbol] + case Some(s) => s.methods + } + + def superclasses: List[ClassSymbol] = + this :: (superclass match { + case None => Nil + case Some(c) => c.superclasses + }); + + def isSubclassOf(that: ClassSymbol): Boolean = + superclasses.contains(that); + + def enterField(f: FieldSymbol): Unit = { + f.offset = fields.size * 4; + fields = fields + f.name -> f; + } + + def lookupField(name: String): Option[FieldSymbol] = + fields.get(name); + + def enterNewMethod(m: MethodSymbol): Unit = { + m.offset = methods.size * 4; + methods = methods + m.name -> m; + } + + def enterMethod(m: MethodSymbol): Unit = { + m.offset = methods(m.name).offset; + methods = methods + m.name -> m; + } + + def lookupMethod(name: String): Option[MethodSymbol] = + methods.get(name); + + def allFields: List[FieldSymbol] = + fields.values.toList; + + def allMethods: List[MethodSymbol] = + methods.values.toList; + + override def toString() = "class " + name; +} + +case class FieldSymbol(pos: Int, name: String, fieldtype: Type) + extends Symbol +{ + override def toString() = "field " + name + ": " + fieldtype; +} + +case class MethodSymbol(pos: Int, name: String, paramtypes: List[Type], restype: Type) + extends Symbol +{ + var address: Int = _; + override def toString() = "method " + name + + paramtypes.mkString("(", ",", ")") + ": " + restype; +} + +case class VarSymbol(pos: Int, name: String, vartype: Type) + extends Symbol +{ + override def toString() = "variable " + name + ": " + vartype; +}