diff options
author | Martin Odersky <odersky@gmail.com> | 2013-03-22 18:03:16 +0100 |
---|---|---|
committer | Martin Odersky <odersky@gmail.com> | 2013-03-22 18:03:16 +0100 |
commit | b440606b0f0d1772d8a1c3bc1c36b3aa3cb576b5 (patch) | |
tree | 0505df934e0bf917269ae1c777e8a627b18b3d16 /src/dotty/tools/dotc/core | |
parent | 5b4f154c9e4c2c6ff48ac68b8d984e306853328f (diff) | |
download | dotty-b440606b0f0d1772d8a1c3bc1c36b3aa3cb576b5.tar.gz dotty-b440606b0f0d1772d8a1c3bc1c36b3aa3cb576b5.tar.bz2 dotty-b440606b0f0d1772d8a1c3bc1c36b3aa3cb576b5.zip |
More fixes for classfile reading.
Including a refactoring of symbol loaders and unpickler traits.
Diffstat (limited to 'src/dotty/tools/dotc/core')
-rw-r--r-- | src/dotty/tools/dotc/core/Printers.scala | 48 | ||||
-rw-r--r-- | src/dotty/tools/dotc/core/Scopes.scala | 2 | ||||
-rw-r--r-- | src/dotty/tools/dotc/core/SymDenotations.scala | 25 | ||||
-rw-r--r-- | src/dotty/tools/dotc/core/SymbolLoaders.scala | 13 | ||||
-rw-r--r-- | src/dotty/tools/dotc/core/TypeOps.scala | 2 | ||||
-rw-r--r-- | src/dotty/tools/dotc/core/pickling/UnPickler.scala | 46 |
6 files changed, 90 insertions, 46 deletions
diff --git a/src/dotty/tools/dotc/core/Printers.scala b/src/dotty/tools/dotc/core/Printers.scala index d271658b2..0f8cc05f9 100644 --- a/src/dotty/tools/dotc/core/Printers.scala +++ b/src/dotty/tools/dotc/core/Printers.scala @@ -293,41 +293,45 @@ object Printers { } /** String representation of symbol's kind. */ - def kindString(sym: Symbol): String = - if (sym isUnsafe PackageClass) "package class" - else if (sym isUnsafe PackageVal) "package" + def kindString(sym: Symbol): String = { + val flags = sym.unsafeFlags + if (flags is PackageClass) "package class" + else if (flags is PackageVal) "package" else if (sym.isPackageObject) if (sym.isClass) "package object class" else "package object" else if (sym.isAnonymousClass) "anonymous class" - else if (sym isUnsafe ModuleClass) "module class" - else if (sym isUnsafe ModuleVal) "module" - else if (sym isUnsafe ImplClass) "implementation class" - else if (sym isUnsafe Trait) "trait" + else if (flags is ModuleClass) "module class" + else if (flags is ModuleVal) "module" + else if (flags is ImplClass) "implementation class" + else if (flags is Trait) "trait" else if (sym.isClass) "class" else if (sym.isType) "type" else if (sym.isGetter) "getter" else if (sym.isSetter) "setter" - else if (sym isUnsafe Lazy) "lazy value" - else if (sym isUnsafe Mutable) "variable" + else if (flags is Lazy) "lazy value" + else if (flags is Mutable) "variable" else if (sym.isClassConstructor && sym.isPrimaryConstructor) "primary constructor" else if (sym.isClassConstructor) "constructor" else if (sym.isSourceMethod) "method" else if (sym.isTerm) "value" else "" + } /** String representation of symbol's definition key word */ - protected def keyString(sym: Symbol): String = - if (sym isUnsafe JavaInterface) "interface" - else if ((sym isUnsafe Trait) && !(sym isUnsafe ImplClass)) "trait" + protected def keyString(sym: Symbol): String = { + val flags = sym.unsafeFlags + if (flags is JavaInterface) "interface" + else if ((flags is Trait) && !(flags is ImplClass)) "trait" else if (sym.isClass) "class" - else if (sym.isType && !(sym isUnsafe ExpandedTypeParam)) "type" - else if (sym isUnsafe Mutable) "var" - else if (sym isUnsafe Package) "package" - else if (sym isUnsafe Module) "object" + else if (sym.isType && !(flags is ExpandedTypeParam)) "type" + else if (flags is Mutable) "var" + else if (flags is Package) "package" + else if (flags is Module) "object" else if (sym.isSourceMethod) "def" - else if (sym.isTerm && (!(sym isUnsafe Param))) "val" + else if (sym.isTerm && (!(flags is Param))) "val" else "" + } /** String representation of symbol's flags */ protected def toTextFlags(sym: Symbol): Text = @@ -478,13 +482,15 @@ object Printers { super.toText(tp, prec) } - override def kindString(sym: Symbol) = - if (sym isUnsafe Package) "package" + override def kindString(sym: Symbol) = { + val flags = sym.unsafeFlags + if (flags is Package) "package" else if (sym.isPackageObject) "package object" - else if (sym isUnsafe Module) "object" - else if (sym isUnsafe ImplClass) "class" + else if (flags is Module) "object" + else if (flags is ImplClass) "class" else if (sym.isClassConstructor) "constructor" else super.kindString(sym) + } override def toTextFlags(sym: Symbol) = Text(sym.flags.flagStrings.filterNot(_.startsWith("<")) map stringToText, " ") diff --git a/src/dotty/tools/dotc/core/Scopes.scala b/src/dotty/tools/dotc/core/Scopes.scala index 2d9df1962..57d9446f1 100644 --- a/src/dotty/tools/dotc/core/Scopes.scala +++ b/src/dotty/tools/dotc/core/Scopes.scala @@ -169,7 +169,7 @@ object Scopes { /** enter a symbol in this scope. */ final def enter[T <: Symbol](sym: T)(implicit ctx: Context): T = { - if (sym.isType) assert(lookup(sym.name) == NoSymbol) // !!! DEBUG + if (sym.isType) assert(lookup(sym.name) == NoSymbol, sym.debugString) // !!! DEBUG newScopeEntry(sym) sym } diff --git a/src/dotty/tools/dotc/core/SymDenotations.scala b/src/dotty/tools/dotc/core/SymDenotations.scala index 42583c5cd..c973fea72 100644 --- a/src/dotty/tools/dotc/core/SymDenotations.scala +++ b/src/dotty/tools/dotc/core/SymDenotations.scala @@ -81,7 +81,8 @@ object SymDenotations { (if (fs <= FromStartFlags) _flags else flags) is fs final def is(fs: FlagConjunction, butNot: FlagSet) = (if (fs <= FromStartFlags && butNot <= FromStartFlags) _flags else flags) is (fs, butNot) - final def isUnsafe(fs: FlagSet) = _flags is fs + + final def unsafeFlags: FlagSet = _flags /** The type info. * The info is an instance of TypeType iff this is a type denotation @@ -102,8 +103,15 @@ object SymDenotations { } } - protected[core] final def info_=(tp: Type) = + protected[core] final def info_=(tp: Type) = { + if ((this is ModuleClass) && !(this is PackageClass)) + tp match { + case ClassInfo(_, _, _, _, ost) => + assert(ost.isInstanceOf[TermRef], tp) + case _ => + } _info = tp + } /** The denotation is completed: all attributes are fully defined */ final def isCompleted: Boolean = ! _info.isInstanceOf[LazyType] @@ -241,7 +249,8 @@ object SymDenotations { } /** Is this denotation static (i.e. with no outer instance)? */ - final def isStatic(implicit ctx: Context) = (this is Static) || owner.isStaticOwner + final def isStatic(implicit ctx: Context) = + (this is Static) || this.exists && owner.isStaticOwner /** Is this a package class or module class that defines static symbols? */ final def isStaticOwner(implicit ctx: Context): Boolean = @@ -421,7 +430,7 @@ object SymDenotations { case ClassInfo(_, _, _, _, selfType: TermRefBySym) if this is ModuleClass => selfType.fixedSym case info: LazyModuleClassInfo => - info.modul + info.module case _ => NoSymbol } @@ -957,12 +966,16 @@ object SymDenotations { /** A lazy type for classes that contains an initial pre-complete scope. * Typically this is for type parameters */ - abstract class LazyClassInfo(val decls: Scope) extends LazyType + trait LazyClassInfo extends LazyType { + val decls: Scope + } /** A lazy type for module classes that points back to the source module. * Needed so that `sourceModule` works before completion. */ - abstract class LazyModuleClassInfo(val modul: TermSymbol) extends LazyClassInfo(newScope) + trait LazyModuleClassInfo extends LazyClassInfo { + def module: TermSymbol + } /** A lazy type for modules that points to the module class. * Needed so that `moduleClass` works before completion. diff --git a/src/dotty/tools/dotc/core/SymbolLoaders.scala b/src/dotty/tools/dotc/core/SymbolLoaders.scala index fa62d29e3..9231a97bf 100644 --- a/src/dotty/tools/dotc/core/SymbolLoaders.scala +++ b/src/dotty/tools/dotc/core/SymbolLoaders.scala @@ -134,10 +134,12 @@ class SymbolLoaders { /** Load contents of a package */ - class PackageLoader(module: TermSymbol, classpath: ClassPath)(implicit val cctx: CondensedContext) - extends LazyModuleClassInfo(module) with SymbolLoader { + class PackageLoader(val module: TermSymbol, classpath: ClassPath)(implicit val cctx: CondensedContext) + extends SymbolLoader with LazyModuleClassInfo { def description = "package loader " + classpath.name + val decls = newScope + def doComplete(root: SymDenotation) { assert(root is PackageClass, root) val pre = root.owner.thisType @@ -197,7 +199,7 @@ class SymbolLoaders { /** A lazy type that completes itself by calling parameter doComplete. * Any linked modules/classes or module classes are also initialized. */ -trait SymbolLoader extends LazyType { +abstract class SymbolLoader extends LazyType { implicit val cctx: CondensedContext /** Load source or class file for `root`, return */ @@ -269,8 +271,9 @@ class SourcefileLoader(val srcfile: AbstractFile)(implicit val cctx: CondensedCo def doComplete(root: SymDenotation): Unit = unsupported("doComplete") } -class ModuleClassCompleter(modul: TermSymbol, classCompleter: SymbolLoader)(implicit val cctx: CondensedContext) - extends LazyModuleClassInfo(modul) with SymbolLoader { +class ModuleClassCompleter(val module: TermSymbol, classCompleter: SymbolLoader)(implicit val cctx: CondensedContext) + extends SymbolLoader with LazyModuleClassInfo { + val decls = newScope def description: String = classCompleter.description override def sourceFileOrNull = classCompleter.sourceFileOrNull def doComplete(root: SymDenotation): Unit = { diff --git a/src/dotty/tools/dotc/core/TypeOps.scala b/src/dotty/tools/dotc/core/TypeOps.scala index aa786d451..38da0ce9c 100644 --- a/src/dotty/tools/dotc/core/TypeOps.scala +++ b/src/dotty/tools/dotc/core/TypeOps.scala @@ -186,6 +186,8 @@ trait TypeOps { this: Context => for ((name, tpe) <- refinements) decls.enter { val formal = formals(name) val bounds = tpe //.toRHS(formal) + assert(decls.lookup(name) == NoSymbol, // DEBUG + s"redefinition of ${decls.lookup(name).debugString} in ${cls.debugString}") ctx.newSymbol(cls, name, formal.flags & RetainedTypeArgFlags, bounds) } parentRefs diff --git a/src/dotty/tools/dotc/core/pickling/UnPickler.scala b/src/dotty/tools/dotc/core/pickling/UnPickler.scala index 4b3f17703..844ddd775 100644 --- a/src/dotty/tools/dotc/core/pickling/UnPickler.scala +++ b/src/dotty/tools/dotc/core/pickling/UnPickler.scala @@ -105,9 +105,15 @@ object UnPickler { case cinfo => (Nil, cinfo) } val parentRefs = ctx.normalizeToRefs(parents, cls, decls) - for (tparam <- tparams) - if (!decls.lookup(tparam.name).exists) decls.enter(tparam) - denot.info = ClassInfo(denot.owner.thisType, denot.classSymbol, parentRefs, decls, optSelfType) + for (tparam <- tparams) { + val tsym = decls.lookup(tparam.name) + if (tsym.exists) tsym.setFlag(TypeParam) + else decls.enter(tparam) + } + var ost = optSelfType + if (ost == NoType && (denot is ModuleClass)) + ost = TermRef(denot.owner.thisType, denot.sourceModule.asTerm) + denot.info = ClassInfo(denot.owner.thisType, denot.classSymbol, parentRefs, decls, ost) } } @@ -402,10 +408,10 @@ class UnPickler(bytes: Array[Byte], classRoot: ClassDenotation, moduleClassRoot: if (isModuleRoot) println(s"moduleRoot of $moduleRoot found at $readIndex, flags = $flags") // !!! DEBUG if (isModuleClassRoot) println(s"moduleClassRoot of $moduleClassRoot found at $readIndex, flags = $flags") // !!! DEBUG - def completeRoot(denot: ClassDenotation): Symbol = { + def completeRoot(denot: ClassDenotation, completer: LazyType): Symbol = { denot.setFlag(flags) denot.resetFlag(Touched) // allow one more completion - denot.info = new RootUnpickler(start, denot.symbol) + denot.info = completer denot.symbol } @@ -432,9 +438,16 @@ class UnPickler(bytes: Array[Byte], classRoot: ClassDenotation, moduleClassRoot: case CLASSsym => val infoRef = readNat() postReadOp = () => atReadPos(index(infoRef), readTypeParams) // force reading type params early, so they get entered in the right order. - if (isClassRoot) completeRoot(classRoot) - else if (isModuleClassRoot) completeRoot(moduleClassRoot) - else cctx.newClassSymbol(owner, name.asTypeName, flags, new LocalClassUnpickler(_), coord = start) + if (isClassRoot) + completeRoot( + classRoot, + new ClassRootUnpickler(start, classRoot.symbol)) + else if (isModuleClassRoot) + completeRoot( + moduleClassRoot, + new ModuleClassRootUnpickler(start, moduleClassRoot.symbol, moduleClassRoot.sourceModule.asTerm)) + else + cctx.newClassSymbol(owner, name.asTypeName, flags, new LocalClassUnpickler(_), coord = start) case MODULEsym | VALsym => if (isModuleRoot) { moduleRoot setFlag flags @@ -445,7 +458,7 @@ class UnPickler(bytes: Array[Byte], classRoot: ClassDenotation, moduleClassRoot: }) } - trait LocalUnpickler extends LazyType { + abstract class LocalUnpickler extends LazyType { def parseToCompletion(denot: SymDenotation) = { val tag = readByte() val end = readNat() + readIndex @@ -490,15 +503,23 @@ class UnPickler(bytes: Array[Byte], classRoot: ClassDenotation, moduleClassRoot: } } - class LocalClassUnpickler(cls: Symbol) extends LazyClassInfo(symScope(cls)) with LocalUnpickler + class LocalClassUnpickler(cls: Symbol) extends LocalUnpickler with LazyClassInfo { + val decls = symScope(cls) + } object localMemberUnpickler extends LocalUnpickler - class RootUnpickler(start: Coord, cls: Symbol) + class ClassRootUnpickler(start: Coord, cls: Symbol) extends LocalClassUnpickler(cls) with SymbolLoaders.SecondCompleter { override def startCoord(denot: SymDenotation): Coord = start } + class ModuleClassRootUnpickler(start: Coord, cls: Symbol, val module: TermSymbol) + extends LocalClassUnpickler(cls) with SymbolLoaders.SecondCompleter with LazyModuleClassInfo { + override def startCoord(denot: SymDenotation): Coord = start + } + + /** Convert * tp { type name = sym } forSome { sym >: L <: H } * to @@ -583,8 +604,7 @@ class UnPickler(bytes: Array[Byte], classRoot: ClassDenotation, moduleClassRoot: } else TypeRef(pre, sym.name.asTypeName) val args = until(end, readTypeRef) if (args.nonEmpty) { // DEBUG - println(s"reading app type $tycon") - println(s"${tycon.typeSymbol.debugString} $args") + println(s"reading app type $tycon $args") } tycon.appliedTo(args) case TYPEBOUNDStpe => |