@@ -95,7 +95,7 @@ object RefChecks {
95
95
* and required classes. Also check that only `enum` constructs extend
96
96
* `java.lang.Enum`.
97
97
*/
98
- private def checkParents (cls : Symbol )(using Context ): Unit = cls.info match {
98
+ private def checkParents (cls : Symbol , parentTrees : List [ Tree ] )(using Context ): Unit = cls.info match {
99
99
case cinfo : ClassInfo =>
100
100
def checkSelfConforms (other : ClassSymbol , category : String , relation : String ) = {
101
101
val otherSelf = other.declaredSelfTypeAsSeenFrom(cls.thisType)
@@ -109,12 +109,26 @@ object RefChecks {
109
109
for (reqd <- cinfo.cls.givenSelfType.classSymbols)
110
110
checkSelfConforms(reqd, " missing requirement" , " required" )
111
111
112
+ def isClassExtendingJavaEnum =
113
+ ! cls.isOneOf(Enum | Trait ) && parents.exists(_.classSymbol == defn.JavaEnumClass )
114
+
112
115
// Prevent wrong `extends` of java.lang.Enum
113
- if ! migrateTo3 &&
114
- ! cls.isOneOf(Enum | Trait ) &&
115
- parents.exists(_.classSymbol == defn.JavaEnumClass )
116
- then
117
- report.error(CannotExtendJavaEnum (cls), cls.sourcePos)
116
+ if isClassExtendingJavaEnum then
117
+ if ! migrateTo3 then // always error, only traits or enum-syntax is possible under scala 3.x
118
+ report.error(CannotExtendJavaEnum (cls), cls.sourcePos)
119
+ else
120
+ // conditionally error, we allow classes to extend java.lang.Enum in scala 2 migration mode,
121
+ // however the no-arg constructor is forbidden, we must look at the parent trees to see
122
+ // which overload is called.
123
+ val javaEnumCtor = defn.JavaEnumClass .primaryConstructor
124
+ parentTrees.exists {
125
+ case parent @ tpd.Apply (tpd.TypeApply (fn, _), _) if fn.tpe.termSymbol eq javaEnumCtor =>
126
+ // here we are simulating the error for missing arguments to a constructor.
127
+ report.error(JavaEnumParentArgs (parent.tpe), cls.sourcePos)
128
+ true
129
+ case _ =>
130
+ false
131
+ }
118
132
119
133
case _ =>
120
134
}
@@ -1089,7 +1103,7 @@ class RefChecks extends MiniPhase { thisPhase =>
1089
1103
override def transformTemplate (tree : Template )(using Context ): Tree = try {
1090
1104
val cls = ctx.owner.asClass
1091
1105
checkOverloadedRestrictions(cls)
1092
- checkParents(cls)
1106
+ checkParents(cls, tree.parents )
1093
1107
if (cls.is(Trait )) tree.parents.foreach(checkParentPrefix(cls, _))
1094
1108
checkCompanionNameClashes(cls)
1095
1109
checkAllOverrides(cls)
0 commit comments