Skip to content

Commit

Permalink
Merge pull request #1324 from Friendseeker/this-context-dependent
Browse files Browse the repository at this point in the history
Avoid spurious recompilations when unrelated constructor with default argument changes
  • Loading branch information
eed3si9n committed Jan 3, 2024
2 parents e5c9bfb + fc22a8e commit cbddcc4
Show file tree
Hide file tree
Showing 8 changed files with 52 additions and 4 deletions.
3 changes: 3 additions & 0 deletions internal/compiler-bridge/src/main/scala/xsbt/ClassName.scala
Expand Up @@ -58,6 +58,9 @@ trait ClassName extends Compat {
protected def constructorNameAsString(cls: Symbol): String =
cls.fullName(';') ++ ";init;"

protected def constructorNameAsString(cls: Symbol, index: String): String =
cls.fullName(';') ++ s";init;default;$index"

/**
* Mangle a JVM symbol name in a format better suited for internal uses by sbt.
*/
Expand Down
21 changes: 17 additions & 4 deletions internal/compiler-bridge/src/main/scala/xsbt/ExtractAPI.scala
Expand Up @@ -327,7 +327,7 @@ class ExtractAPI[GlobalType <: Global](
case returnType =>
val retType = processType(in, dropConst(returnType))
xsbti.api.Def.of(
simpleName(s),
simpleNameForMethod(s),
getAccess(s),
getModifiers(s),
annotations(in, s),
Expand Down Expand Up @@ -827,9 +827,22 @@ class ExtractAPI[GlobalType <: Global](
}

private def simpleName(s: Symbol): String = {
val n = s.unexpandedName
val n2 = if (n == nme.CONSTRUCTOR) constructorNameAsString(s.enclClass) else n.decode.toString
n2.trim
s.unexpandedName.decode.trim
}

private def simpleNameForMethod(s: Symbol): String = {
val name = s.unexpandedName
val untrimmedName = if (name == nme.CONSTRUCTOR)
constructorNameAsString(s.enclClass)
else {
val decoded = name.decode
val constructorWithDefaultArgument = "<init>\\$default\\$(\\d+)".r
decoded match {
case constructorWithDefaultArgument(index) => constructorNameAsString(s.enclClass, index)
case _ => decoded
}
}
untrimmedName.trim
}

private def staticAnnotations(annotations: List[AnnotationInfo]): List[AnnotationInfo] =
Expand Down
@@ -0,0 +1,4 @@
class A {
var z = B.z // introduce a member ref dependency to B
var c: C = new C(1)
}
@@ -0,0 +1,7 @@
class B(val z: Int) {
def this(x: Int, y: Int = 2) = this(x + y)
}

object B {
val z = 1
}
@@ -0,0 +1,3 @@
class C(z: String) {
def this(x: Int, y: Int = 2) = this("")
}
@@ -0,0 +1,7 @@
class B(val z: Int) {
def this(x: Int, y: String = "") = this(x + y.toInt)
}

object B {
val z = 1
}
@@ -0,0 +1,3 @@
class C(z: String) {
def this(x: Boolean, y: Int = 2) = this("")
}
@@ -0,0 +1,8 @@
> compile
$ copy-file changes/B.scala B.scala
# Second compilation round, there should be no third round (we don't need to recompile A.scala)
> compile
# Check that there were only two rounds of compilation
> checkIterations 2
$ copy-file changes/C.scala C.scala
-> compile

0 comments on commit cbddcc4

Please sign in to comment.