Skip to content

Commit

Permalink
Browse files Browse the repository at this point in the history
Add sealedDescendants method to
SymDenotation - recursive children
of a symbol
  • Loading branch information
bishabosha committed May 28, 2021
1 parent a956774 commit b57d62a
Show file tree
Hide file tree
Showing 7 changed files with 56 additions and 1 deletion.
20 changes: 20 additions & 0 deletions compiler/src/dotty/tools/dotc/core/SymDenotations.scala
Original file line number Diff line number Diff line change
Expand Up @@ -1614,6 +1614,26 @@ object SymDenotations {

annotations.collect { case Annotation.Child(child) => child }.reverse
end children

/** Recursively assemble all children of this symbol, including this symbol.
* Preserves order of insertion.
*/
final def sealedDescendants(using Context): List[Symbol] =
@tailrec
def loop(syms: List[Symbol], acc: List[Symbol]): List[Symbol] = syms match
case sym :: syms1 =>
val notSeen = sym.children.filterConserve(!acc.contains(_))
if notSeen.isEmpty then
loop(syms1, acc)
else
loop(syms1 ::: notSeen, acc ::: notSeen)
case nil =>
acc
end loop

val lvl1 = children
loop(lvl1, this.symbol::lvl1)
end sealedDescendants
}

/** The contents of a class definition during a period
Expand Down
2 changes: 1 addition & 1 deletion compiler/src/dotty/tools/dotc/sbt/ExtractAPI.scala
Original file line number Diff line number Diff line change
Expand Up @@ -221,7 +221,7 @@ private class ExtractAPICollector(using Context) extends ThunkHolder {
val modifiers = apiModifiers(sym)
val anns = apiAnnotations(sym).toArray
val topLevel = sym.isTopLevelClass
val childrenOfSealedClass = sym.children.sorted(classFirstSort).map(c =>
val childrenOfSealedClass = sym.sealedDescendants.sorted(classFirstSort).map(c =>
if (c.isClass)
apiType(c.typeRef)
else
Expand Down
4 changes: 4 additions & 0 deletions sbt-test/source-dependencies/sealed-extends-sealed/A.scala
Original file line number Diff line number Diff line change
@@ -0,0 +1,4 @@
sealed trait Z
sealed trait A extends Z
class B extends A
class C extends A
6 changes: 6 additions & 0 deletions sbt-test/source-dependencies/sealed-extends-sealed/App.scala
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
object App {
def foo(z: Z) = z match {
case _: B =>
case _: C =>
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
sealed trait Z
sealed trait A extends Z
class B extends A
class C extends A
class D extends A
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
import sbt._
import Keys._

object DottyInjectedPlugin extends AutoPlugin {
override def requires = plugins.JvmPlugin
override def trigger = allRequirements

override val projectSettings = Seq(
scalaVersion := sys.props("plugin.scalaVersion"),
scalacOptions ++= Seq("-source:3.0-migration", "-Xfatal-warnings")
)
}
8 changes: 8 additions & 0 deletions sbt-test/source-dependencies/sealed-extends-sealed/test
Original file line number Diff line number Diff line change
@@ -0,0 +1,8 @@
> compile

# Introduce a new class C that also extends A
$ copy-file changes/A.scala A.scala

# App.scala needs recompiling because the pattern match in it
# is no longer exhaustive, which emits a warning
-> compile

0 comments on commit b57d62a

Please sign in to comment.