@@ -484,7 +484,7 @@ class Namer { typer: Typer =>
484
484
/** Create top-level symbols for statements and enter them into symbol table */
485
485
def index (stats : List [Tree ])(implicit ctx : Context ): Context = {
486
486
487
- // module name -> (stat, moduleCls / moduleVal)
487
+ // module name -> (stat, moduleCls | moduleVal)
488
488
val moduleClsDef = mutable.Map [TypeName , (Tree , TypeDef )]()
489
489
val moduleValDef = mutable.Map [TermName , (Tree , ValDef )]()
490
490
@@ -512,49 +512,54 @@ class Namer { typer: Typer =>
512
512
res
513
513
}
514
514
515
+ /** Merge `fromCls` of `fromStat` into `toCls` of `toStat`
516
+ * if the former is synthetic and the latter not.
517
+ *
518
+ * Note:
519
+ * 1. `fromStat` and `toStat` could be the same stat
520
+ * 2. `fromCls` and `toCls` are necessarily different
521
+ */
522
+ def mergeIfSynthetic (fromStat : Tree , fromCls : TypeDef , toStat : Tree , toCls : TypeDef ): Unit =
523
+ if (fromCls.mods.is(Synthetic ) && ! toCls.mods.is(Synthetic )) {
524
+ removeInExpanded(fromStat, fromCls)
525
+ val mcls = mergeModuleClass(toStat, toCls, fromCls.rhs.asInstanceOf [Template ].body)
526
+ moduleClsDef(fromCls.name) = (toStat, mcls)
527
+ }
528
+
515
529
/** Merge the definitions of a synthetic companion generated by a case class
516
530
* and the real companion, if both exist.
517
531
*/
518
532
def mergeCompanionDefs () = {
519
- def valid (mdef : MemberDef ): Boolean = ! mdef.mods.is(Package ) && mdef.mods.is( Module )
533
+ def valid (mdef : MemberDef ): Boolean = mdef.mods.is(Module , butNot = Package )
520
534
521
535
for (stat <- stats)
522
536
expanded(stat) match {
523
537
case Thicket (trees) => // companion object always expands to thickets
524
538
trees.map {
525
539
case mcls @ TypeDef (name, impl : Template ) if valid(mcls) =>
526
- if (moduleClsDef.contains(name)) {
527
- val (stat1, mcls1 @ TypeDef (_, impl1 : Template )) = moduleClsDef(name)
528
- if (mcls.mods.is(Synthetic ) && ! mcls1.mods.is(Synthetic )) { // merge synthetic into user-defined module
529
- removeInExpanded(stat, mcls)
530
- val mcls2 = mergeModuleClass(stat1, mcls1, impl.body)
531
- moduleClsDef(name) = (stat1, mcls2)
532
- }
533
- else if (! mcls.mods.is(Synthetic ) && mcls1.mods.is(Synthetic )) {
534
- removeInExpanded(stat1, mcls1)
535
- val mcls2 = mergeModuleClass(stat, mcls, impl1.body)
536
- moduleClsDef(name) = (stat, mcls2)
537
- }
538
- else {
539
- // redefinition of objects or case classes, handled elsewhere
540
- }
540
+ moduleClsDef.get(name) match {
541
+ case Some ((stat1, mcls1@ TypeDef (_, impl1 : Template ))) =>
542
+ mergeIfSynthetic(stat, mcls, stat1, mcls1)
543
+ mergeIfSynthetic(stat1, mcls1, stat, mcls)
544
+ case None =>
545
+ moduleClsDef(name) = (stat, mcls)
541
546
}
542
- else moduleClsDef(name) = (stat, mcls)
543
547
544
548
case vdef @ ValDef (name, _, _) if valid(vdef) =>
545
- if (moduleValDef.contains(name)) {
546
- val (stat1, vdef1) = moduleValDef(name)
547
- if (vdef.mods.is(Synthetic ) && ! vdef1.mods.is(Synthetic )) // merge synthetic into user-defined module
548
- removeInExpanded(stat, vdef)
549
- else if (! vdef.mods.is(Synthetic ) && vdef1.mods.is(Synthetic )) {
550
- removeInExpanded(stat1, vdef1)
549
+ moduleValDef.get(name) match {
550
+ case Some ((stat1, vdef1)) =>
551
+ if (vdef.mods.is(Synthetic ) && ! vdef1.mods.is(Synthetic ))
552
+ removeInExpanded(stat, vdef)
553
+ else if (! vdef.mods.is(Synthetic ) && vdef1.mods.is(Synthetic )) {
554
+ removeInExpanded(stat1, vdef1)
555
+ moduleValDef(name) = (stat, vdef)
556
+ }
557
+ else {
558
+ // double definition of objects or case classes, handled elsewhere
559
+ }
560
+ case None =>
551
561
moduleValDef(name) = (stat, vdef)
552
- }
553
- else {
554
- // redefinition of objects or case classes, handled elsewhere
555
- }
556
562
}
557
- else moduleValDef(name) = (stat, vdef)
558
563
559
564
case _ =>
560
565
}
0 commit comments