Thanks to visit codestin.com
Credit goes to github.com

Skip to content

Commit 87ce314

Browse files
committed
Constructors handles private local early defs
Improve name unexpansion for early def
1 parent 701ca74 commit 87ce314

File tree

2 files changed

+37
-15
lines changed

2 files changed

+37
-15
lines changed

src/compiler/scala/tools/nsc/transform/Constructors.scala

Lines changed: 25 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -14,7 +14,7 @@ package scala.tools.nsc
1414
package transform
1515

1616
import scala.annotation._
17-
import scala.collection.mutable
17+
import scala.collection.mutable, mutable.ListBuffer
1818
import scala.reflect.internal.util.ListOfNil
1919
import scala.tools.nsc.Reporting.WarningCategory
2020
import symtab.Flags._
@@ -29,8 +29,7 @@ abstract class Constructors extends Statics with Transform with TypingTransforme
2929
/** the following two members override abstract members in Transform */
3030
val phaseName: String = "constructors"
3131

32-
protected def newTransformer(unit: CompilationUnit): AstTransformer =
33-
new ConstructorTransformer(unit)
32+
protected def newTransformer(unit: CompilationUnit): AstTransformer = new ConstructorTransformer(unit)
3433

3534
private val guardedCtorStats: mutable.Map[Symbol, List[Tree]] = perRunCaches.newMap[Symbol, List[Tree]]()
3635
private val ctorParams: mutable.Map[Symbol, List[Symbol]] = perRunCaches.newMap[Symbol, List[Symbol]]()
@@ -155,8 +154,8 @@ abstract class Constructors extends Statics with Transform with TypingTransforme
155154
* Finally, the whole affair of eliding is avoided for DelayedInit subclasses,
156155
* given that for them usually nothing gets elided anyway.
157156
* That's a consequence from re-locating the post-super-calls statements from their original location
158-
* (the primary constructor) into a dedicated synthetic method that an anon-closure may invoke, as required by DelayedInit.
159-
*
157+
* (the primary constructor) into a dedicated synthetic method that an anon-closure may invoke,
158+
* as required by DelayedInit.
160159
*/
161160
private trait OmittablesHelper {
162161
def computeOmittableAccessors(clazz: Symbol, defs: List[Tree], auxConstructors: List[Tree], @unused constructor: List[Tree]): Set[Symbol] = {
@@ -337,7 +336,7 @@ abstract class Constructors extends Statics with Transform with TypingTransforme
337336
* `specializedStats` are replaced by the specialized assignment.
338337
*/
339338
private def mergeConstructors(genericClazz: Symbol, originalStats: List[Tree], specializedStats: List[Tree]): List[Tree] = {
340-
val specBuf = new mutable.ListBuffer[Tree]
339+
val specBuf = ListBuffer.empty[Tree]
341340
specBuf ++= specializedStats
342341

343342
def specializedAssignFor(sym: Symbol): Option[Tree] =
@@ -466,11 +465,15 @@ abstract class Constructors extends Statics with Transform with TypingTransforme
466465
private val stats = impl.body // the transformed template body
467466

468467
// find and dissect primary constructor
469-
private val (primaryConstr, _primaryConstrParams, primaryConstrBody) = stats collectFirst {
470-
case dd@DefDef(_, _, _, vps :: Nil, _, rhs: Block) if dd.symbol.isPrimaryConstructor => (dd, vps map (_.symbol), rhs)
471-
} getOrElse {
472-
abort("no constructor in template: impl = " + impl)
473-
}
468+
private val (primaryConstr, _primaryConstrParams, primaryConstrBody) =
469+
stats.collectFirst {
470+
case dd @ DefDef(_, _, _, vps :: Nil, _, rhs: Block)
471+
if dd.symbol.isPrimaryConstructor =>
472+
(dd, vps.map(_.symbol), rhs)
473+
}
474+
.getOrElse {
475+
abort("no constructor in template: impl = " + impl)
476+
}
474477

475478
def primaryConstrParams = _primaryConstrParams
476479
def usesSpecializedField = intoConstructor.usesSpecializedField
@@ -594,7 +597,7 @@ abstract class Constructors extends Statics with Transform with TypingTransforme
594597
* - `classInitStats`: statements that go into the class initializer
595598
*/
596599
class Triage {
597-
private val defBuf, auxConstructorBuf, constrPrefixBuf, constrStatBuf, classInitStatBuf = new mutable.ListBuffer[Tree]
600+
private val defBuf, auxConstructorBuf, constrPrefixBuf, constrStatBuf, classInitStatBuf = ListBuffer.empty[Tree]
598601

599602
triage()
600603

@@ -617,8 +620,15 @@ abstract class Constructors extends Statics with Transform with TypingTransforme
617620
stat match {
618621
case ValDef(mods, name, _, _) if mods.hasFlag(PRESUPER) => // TODO trait presupers
619622
// stat is the constructor-local definition of the field value
620-
val fields = presupers filter (_.getterName == name)
621-
assert(fields.length == 1, s"expected exactly one field by name $name in $presupers of $clazz's early initializers")
623+
val fields = presupers.filter { v =>
624+
val nm =
625+
if (v.symbol.isPrivateLocal && v.symbol.hasFlag(EXPANDEDNAME))
626+
v.symbol.unexpandedName.dropLocal
627+
else
628+
v.getterName
629+
nm == name
630+
}
631+
assert(fields.length == 1, s"expected exactly one field by name $name in $presupers of $clazz's early initializers but saw $fields")
622632
val to = fields.head.symbol
623633

624634
if (memoizeValue(to)) constrStatBuf += mkAssign(to, Ident(stat.symbol))
@@ -789,7 +799,7 @@ abstract class Constructors extends Statics with Transform with TypingTransforme
789799

790800
// Eliminate all field/accessor definitions that can be dropped from template
791801
// We never eliminate delayed hooks or the constructors, so, only filter `defs`.
792-
val prunedStats = (defs filterNot omittableStat) ::: delayedHookDefs ::: constructors
802+
val prunedStats = defs.filterNot(omittableStat) ::: delayedHookDefs ::: constructors
793803

794804
val statsWithInitChecks =
795805
if (settings.checkInit.value) {

test/files/pos/t10561.scala

Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,12 @@
1+
2+
class Parent {
3+
private val field: Int = 3
4+
}
5+
6+
class Child(n: Int) extends {
7+
private val field = n
8+
} with Parent {
9+
class Inner {
10+
def f = field
11+
}
12+
}

0 commit comments

Comments
 (0)