aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--src/dotty/tools/dotc/core/Contexts.scala2
-rw-r--r--src/dotty/tools/dotc/core/Denotations.scala22
-rw-r--r--src/dotty/tools/dotc/core/Flags.scala4
-rw-r--r--src/dotty/tools/dotc/core/Printers.scala45
-rw-r--r--src/dotty/tools/dotc/core/SymDenotations.scala12
-rw-r--r--src/dotty/tools/dotc/core/SymbolLoaders.scala11
-rw-r--r--src/dotty/tools/dotc/core/Types.scala12
-rw-r--r--src/dotty/tools/dotc/core/pickling/UnPickler.scala15
-rw-r--r--src/dotty/tools/dotc/util/Text.scala1
-rw-r--r--src/test/showClass.scala41
10 files changed, 113 insertions, 52 deletions
diff --git a/src/dotty/tools/dotc/core/Contexts.scala b/src/dotty/tools/dotc/core/Contexts.scala
index 2759d1079..6dfd2050d 100644
--- a/src/dotty/tools/dotc/core/Contexts.scala
+++ b/src/dotty/tools/dotc/core/Contexts.scala
@@ -256,7 +256,7 @@ object Contexts {
.withSetting(settings.debug, true)
.withSetting(settings.Ylogcp, true)
.withSetting(settings.printtypes, true)
- .withSetting(settings.pageWidth, 120)
+ .withSetting(settings.pageWidth, 90)
/** The symbol loaders */
val loaders = new SymbolLoaders
diff --git a/src/dotty/tools/dotc/core/Denotations.scala b/src/dotty/tools/dotc/core/Denotations.scala
index 24008ab63..f8837fafe 100644
--- a/src/dotty/tools/dotc/core/Denotations.scala
+++ b/src/dotty/tools/dotc/core/Denotations.scala
@@ -463,15 +463,25 @@ object Denotations {
final def first = this
final def toDenot(implicit ctx: Context) = this
final def containsSig(sig: Signature)(implicit ctx: Context) =
- signature == sig
+ exists && signature == sig
final def filterDisjoint(denots: PreDenotation)(implicit ctx: Context): SingleDenotation =
if (denots.containsSig(signature)) NoDenotation else this
final def filterExcluded(excluded: FlagSet)(implicit ctx: Context): SingleDenotation =
- if (excluded != EmptyFlags && (asSymDenotation is excluded)) NoDenotation
- else this
- def asSeenFrom(pre: Type)(implicit ctx: Context): SingleDenotation =
- if (!asSymDenotation.owner.membersNeedAsSeenFrom(pre)) this
- else derivedSingleDenotation(symbol, info.asSeenFrom(pre, asSymDenotation.owner))
+ if (excluded == EmptyFlags) this
+ else this match {
+ case thisd: SymDenotation =>
+ if (thisd is excluded) NoDenotation else this
+ case _ =>
+ if (symbol is excluded) NoDenotation else this
+ }
+ def asSeenFrom(pre: Type)(implicit ctx: Context): SingleDenotation = {
+ val owner = this match {
+ case thisd: SymDenotation => thisd.owner
+ case _ => if (symbol.exists) symbol.owner else NoSymbol
+ }
+ if (!owner.membersNeedAsSeenFrom(pre)) this
+ else derivedSingleDenotation(symbol, info.asSeenFrom(pre, owner))
+ }
}
class UniqueRefDenotation(
diff --git a/src/dotty/tools/dotc/core/Flags.scala b/src/dotty/tools/dotc/core/Flags.scala
index ff0a2e0ee..43d5e5cd1 100644
--- a/src/dotty/tools/dotc/core/Flags.scala
+++ b/src/dotty/tools/dotc/core/Flags.scala
@@ -220,6 +220,8 @@ object Flags {
/** Labeled with `sealed` modifier (sealed class) */
final val Sealed = typeFlag(11, "sealed")
+ final val AccessorOrSealed = Accessor.toCommonFlags
+
/** A mutable var */
final val Mutable = termFlag(12, "mutable")
@@ -369,7 +371,7 @@ object Flags {
/** Flags guaranteed to be set upon symbol creation */
final val FromStartFlags =
AccessFlags | Module | Package | Deferred | Param | Scala2ExistentialCommon | Touched |
- Static | CovariantCommon | ContravariantCommon | ExpandedName
+ Static | CovariantCommon | ContravariantCommon | ExpandedName | AccessorOrSealed
assert(FromStartFlags.isTermFlags && FromStartFlags.isTypeFlags)
// TODO: Should check that FromStartFlags do not changed in completion
diff --git a/src/dotty/tools/dotc/core/Printers.scala b/src/dotty/tools/dotc/core/Printers.scala
index e6b2288ab..d271658b2 100644
--- a/src/dotty/tools/dotc/core/Printers.scala
+++ b/src/dotty/tools/dotc/core/Printers.scala
@@ -96,6 +96,9 @@ object Printers {
try {
ctx.toTextRecursions += 1
op
+ } catch {
+ case ex: CyclicReference =>
+ "<cycle involving ${ex.denot}>"
} finally {
ctx.toTextRecursions -= 1
}
@@ -165,11 +168,11 @@ object Printers {
Text(refined.map(toTextRefinement), "; ").close ~ "}"
case AndType(tp1, tp2) =>
(prec parenthesize AndPrec) {
- toText(tp1, AndPrec) ~ "&" ~ toText(tp2, AndPrec)
+ toText(tp1, AndPrec) ~ " & " ~ toText(tp2, AndPrec)
}
case OrType(tp1, tp2) =>
(prec parenthesize OrPrec) {
- toText(tp1, OrPrec) ~ "|" ~ toText(tp2, OrPrec)
+ toText(tp1, OrPrec) ~ " | " ~ toText(tp2, OrPrec)
}
case ErrorType =>
"<error>"
@@ -282,7 +285,7 @@ object Printers {
else Text()
val parentsText = Text(cparents.map(toText(_, WithPrec)), " with ")
val declsText = if (decls.isEmpty) Text() else dclsText(decls.toList)
- "extends " ~ parentsText ~ "{" ~ selfText ~ declsText ~
+ " extends " ~ parentsText ~ "{" ~ selfText ~ declsText ~
"} at " ~ preText
case _ =>
": " ~ toTextGlobal(tp)
@@ -291,22 +294,22 @@ object Printers {
/** String representation of symbol's kind. */
def kindString(sym: Symbol): String =
- if (sym is PackageClass) "package class"
- else if (sym is PackageVal) "package"
+ if (sym isUnsafe PackageClass) "package class"
+ else if (sym isUnsafe PackageVal) "package"
else if (sym.isPackageObject)
if (sym.isClass) "package object class"
else "package object"
else if (sym.isAnonymousClass) "anonymous class"
- else if (sym is ModuleClass) "module class"
- else if (sym is ModuleVal) "module"
- else if (sym is ImplClass) "implementation class"
- else if (sym is Trait) "trait"
+ 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 (sym.isClass) "class"
else if (sym.isType) "type"
else if (sym.isGetter) "getter"
else if (sym.isSetter) "setter"
- else if (sym is Lazy) "lazy value"
- else if (sym is Mutable) "variable"
+ else if (sym isUnsafe Lazy) "lazy value"
+ else if (sym isUnsafe Mutable) "variable"
else if (sym.isClassConstructor && sym.isPrimaryConstructor) "primary constructor"
else if (sym.isClassConstructor) "constructor"
else if (sym.isSourceMethod) "method"
@@ -315,15 +318,15 @@ object Printers {
/** String representation of symbol's definition key word */
protected def keyString(sym: Symbol): String =
- if (sym is JavaInterface) "interface"
- else if (sym is (Trait, butNot = ImplClass)) "trait"
+ if (sym isUnsafe JavaInterface) "interface"
+ else if ((sym isUnsafe Trait) && !(sym isUnsafe ImplClass)) "trait"
else if (sym.isClass) "class"
- else if (sym.isType && !(sym is ExpandedTypeParam)) "type"
- else if (sym is Mutable) "var"
- else if (sym is Package) "package"
- else if (sym is Module) "object"
+ 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.isSourceMethod) "def"
- else if (sym.isTerm && (!(sym is Param))) "val"
+ else if (sym.isTerm && (!(sym isUnsafe Param))) "val"
else ""
/** String representation of symbol's flags */
@@ -476,10 +479,10 @@ object Printers {
}
override def kindString(sym: Symbol) =
- if (sym is Package) "package"
+ if (sym isUnsafe Package) "package"
else if (sym.isPackageObject) "package object"
- else if (sym is Module) "object"
- else if (sym is ImplClass) "class"
+ else if (sym isUnsafe Module) "object"
+ else if (sym isUnsafe ImplClass) "class"
else if (sym.isClassConstructor) "constructor"
else super.kindString(sym)
diff --git a/src/dotty/tools/dotc/core/SymDenotations.scala b/src/dotty/tools/dotc/core/SymDenotations.scala
index d5ccfb74a..42583c5cd 100644
--- a/src/dotty/tools/dotc/core/SymDenotations.scala
+++ b/src/dotty/tools/dotc/core/SymDenotations.scala
@@ -81,6 +81,7 @@ 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
/** The type info.
* The info is an instance of TypeType iff this is a type denotation
@@ -107,6 +108,8 @@ object SymDenotations {
/** The denotation is completed: all attributes are fully defined */
final def isCompleted: Boolean = ! _info.isInstanceOf[LazyType]
+ final def isCompleting: Boolean = (_flags is Touched) && !isCompleted
+
/** The completer of this denotation. @pre: Denotation is not yet completed */
final def completer: LazyType = _info.asInstanceOf[LazyType]
@@ -803,10 +806,19 @@ object SymDenotations {
private def computeMembersNamed(name: Name)(implicit ctx: Context): PreDenotation =
if (!classSymbol.hasChildren || (memberFingerPrint contains name)) {
val ownDenots = info.decls.denotsNamed(name)
+// if (name.toString == "GenericCanBuildFrom") // DEBUG
+// println(s"$this.member(GenericCanBuildFrom), ownDenots = $ownDenots")
def collect(denots: PreDenotation, parents: List[TypeRef]): PreDenotation = parents match {
case p :: ps =>
val denots1 = p.symbol.denot match {
case parentd: ClassDenotation =>
+// if (name.toString == "GenericCanBuildFrom") { // DEBUG
+// val s1 = parentd.membersNamed(name)
+// val s2 = s1.filterExcluded(Private)
+// val s3 = s2.asSeenFrom(thisType)
+// val s4 = s3.filterDisjoint(ownDenots)
+// println(s"$this.member(GenericCanBuildFrom) $s1 $s2 $s3 $s4")
+// }
denots union
parentd.membersNamed(name)
.filterExcluded(Private)
diff --git a/src/dotty/tools/dotc/core/SymbolLoaders.scala b/src/dotty/tools/dotc/core/SymbolLoaders.scala
index b71b0c660..fa62d29e3 100644
--- a/src/dotty/tools/dotc/core/SymbolLoaders.scala
+++ b/src/dotty/tools/dotc/core/SymbolLoaders.scala
@@ -15,6 +15,13 @@ import StdNames._
import Decorators.StringDecorator
import pickling.ClassfileParser
+object SymbolLoaders {
+ /** A marker trait for a completer that replaces the original
+ * Symbol loader for an unpickled root.
+ */
+ trait SecondCompleter
+}
+
/** A base class for Symbol loaders with some overridable behavior */
class SymbolLoaders {
@@ -225,7 +232,9 @@ trait SymbolLoader extends LazyType {
throw ex
} finally {
def postProcess(denot: SymDenotation) =
- if ((denot is Touched) && !denot.isCompleted) denot.markAbsent()
+ if (!denot.isCompleted &&
+ !denot.completer.isInstanceOf[SymbolLoaders.SecondCompleter])
+ denot.markAbsent()
postProcess(root)
if (!root.isRoot)
postProcess(root.linkedClass.denot)
diff --git a/src/dotty/tools/dotc/core/Types.scala b/src/dotty/tools/dotc/core/Types.scala
index 252901b17..b061a1227 100644
--- a/src/dotty/tools/dotc/core/Types.scala
+++ b/src/dotty/tools/dotc/core/Types.scala
@@ -551,7 +551,13 @@ object Types {
}
def hkRefinement(tp: TypeRef): Type = {
- val hkArgs = hkApp(tp.info).typeArgs
+ val hkArgs =
+ if (tp.symbol.isCompleting)
+ // This can happen if a higher-kinded type appears applied to arguments in its own bounds.
+ // TODO: Catch this case and mark as "proceed at own risk" later.
+ args map (_ => defn.InvariantBetweenClass.typeConstructor)
+ else
+ hkApp(tp.info).typeArgs
((tp: Type) /: hkArgs.zipWithIndex.zip(args)) {
case (parent, ((hkArg, idx), arg)) =>
val vsym = hkArg.typeSymbol
@@ -1627,6 +1633,10 @@ object Types {
name.isTermName && (pre member name).hasAltWith(_ is Deferred)
}
+ object takeAllFilter extends NameFilter {
+ def apply(pre: Type, name: Name)(implicit ctx: Context): Boolean = true
+ }
+
// ----- Exceptions -------------------------------------------------------------
class TypeError(msg: String) extends Exception(msg)
diff --git a/src/dotty/tools/dotc/core/pickling/UnPickler.scala b/src/dotty/tools/dotc/core/pickling/UnPickler.scala
index 2f7bcc94d..4b3f17703 100644
--- a/src/dotty/tools/dotc/core/pickling/UnPickler.scala
+++ b/src/dotty/tools/dotc/core/pickling/UnPickler.scala
@@ -135,7 +135,7 @@ class UnPickler(bytes: Array[Byte], classRoot: ClassDenotation, moduleClassRoot:
import cctx.debug
val moduleRoot = moduleClassRoot.sourceModule.denot
- println(s"moduleRoot = $moduleRoot, ${moduleRoot.isTerm}") // !!! DEBUG
+ assert(moduleRoot.isTerm)
checkVersion()
@@ -494,7 +494,8 @@ class UnPickler(bytes: Array[Byte], classRoot: ClassDenotation, moduleClassRoot:
object localMemberUnpickler extends LocalUnpickler
- class RootUnpickler(start: Coord, cls: Symbol) extends LocalClassUnpickler(cls) {
+ class RootUnpickler(start: Coord, cls: Symbol)
+ extends LocalClassUnpickler(cls) with SymbolLoaders.SecondCompleter {
override def startCoord(denot: SymDenotation): Coord = start
}
@@ -581,7 +582,10 @@ class UnPickler(bytes: Array[Byte], classRoot: ClassDenotation, moduleClassRoot:
sym.asType)
} else TypeRef(pre, sym.name.asTypeName)
val args = until(end, readTypeRef)
- if (args.nonEmpty) println(s"reading app type $tycon ${tycon.typeSymbol.debugString} $args, owner = ${tycon.typeSymbol.owner.debugString}") // !!! DEBUG
+ if (args.nonEmpty) { // DEBUG
+ println(s"reading app type $tycon")
+ println(s"${tycon.typeSymbol.debugString} $args")
+ }
tycon.appliedTo(args)
case TYPEBOUNDStpe =>
TypeBounds(readTypeRef(), readTypeRef())
@@ -606,7 +610,10 @@ class UnPickler(bytes: Array[Byte], classRoot: ClassDenotation, moduleClassRoot:
case METHODtpe | IMPLICITMETHODtpe =>
val restpe = readTypeRef()
val params = until(end, readSymbolRef)
- val maker = if (tag == METHODtpe) MethodType else ImplicitMethodType
+ def isImplicit =
+ tag == IMPLICITMETHODtpe ||
+ params.nonEmpty && (params.head is Implicit)
+ val maker = if (isImplicit) ImplicitMethodType else MethodType
maker.fromSymbols(params, restpe)
case POLYtpe =>
val restpe = readTypeRef()
diff --git a/src/dotty/tools/dotc/util/Text.scala b/src/dotty/tools/dotc/util/Text.scala
index 251274371..a314e8ab4 100644
--- a/src/dotty/tools/dotc/util/Text.scala
+++ b/src/dotty/tools/dotc/util/Text.scala
@@ -45,6 +45,7 @@ object Texts {
this match {
case Str(s1) => Str(s1 + s2)
case Fluid(Str(s1) :: prev) => Fluid(Str(s1 + s2) :: prev)
+ case Fluid(relems) => Fluid(that :: relems)
}
case Fluid(relems) =>
(this /: relems.reverse)(_ appendToLastLine _)
diff --git a/src/test/showClass.scala b/src/test/showClass.scala
index a7896c733..cecc99684 100644
--- a/src/test/showClass.scala
+++ b/src/test/showClass.scala
@@ -2,16 +2,23 @@ package test
import dotty.tools.dotc.core._
import Contexts._
-import Symbols._, Types._
+import Symbols._, Types._, dotty.tools.dotc.util.Texts._
import Decorators._
object showClass {
- def showClass(path: String)(implicit ctx: Context): Unit = {
+ def showClasses(path: String)(implicit ctx: Context): Unit = {
+ def showClass(cls: Symbol) = {
+ println(s"showing $path -> ${cls.denot}")
+ val cinfo = cls.info
+ val infoText: Text = if (cinfo.exists) cinfo.toText else " is missing"
+ println("======================================")
+ println((cls.toText ~ infoText).show)
+ }
println(s"showing $path")
val cls = ctx.requiredClass(path.toTypeName)
- println(s"showing $path -> ${cls.denot}")
- println((cls.toText ~ cls.info.toText).show)
+ showClass(cls)
+// showClass(cls.linkedClass)
/*
val info = cls.info
info match {
@@ -33,20 +40,20 @@ object showClass {
println(ctx.settings)
base.definitions.init()
- for (arg <- args) showClass(arg)
+ for (arg <- args) showClasses(arg)
-// showClass("java.lang.Class")
-// showClass("scala.Boolean")
-// showClass("scala.Array")
-// showClass("scala.math.Ordering")
-// showClass("scala.collection.Traversable")
-// showClass("scala.collection.LinearSeqLike")
-// showClass("scala.collection.immutable.List")
- showClass("scala.collection.TraversableLike")
-// showClass("scala.collection.immutable.Seq")
-// showClass("scala.collection.MapLike")
-// showClass("scala.Function1")
-// showClass("dotty.tools.dotc.core.Types")
+ showClasses("java.lang.Class")
+ showClasses("scala.Boolean")
+ showClasses("scala.Array")
+ showClasses("scala.math.Ordering")
+ showClasses("scala.collection.Traversable")
+// showClasses("scala.collection.LinearSeqLike")
+// showClasses("scala.collection.immutable.List")
+// showClasses("scala.collection.TraversableLike")
+// showClasses("scala.collection.generic.package")
+// showClasses("scala.collection.MapLike")
+// showClasses("scala.Function1")
+// showClasses("dotty.tools.dotc.core.Types")
println("done")
}
} \ No newline at end of file