@@ -250,7 +250,8 @@ object desugar {
250
250
251
251
/** The expansion of a class definition. See inline comments for what is involved */
252
252
def classDef (cdef : TypeDef )(implicit ctx : Context ): Tree = {
253
- val TypeDef (name, impl @ Template (constr0, parents, self, _)) = cdef
253
+ val className = checkNotReservedName(cdef).asTypeName
254
+ val impl @ Template (constr0, parents, self, _) = cdef.rhs
254
255
val mods = cdef.mods
255
256
val companionMods = mods.withFlags((mods.flags & AccessFlags ).toCommonFlags)
256
257
@@ -384,7 +385,7 @@ object desugar {
384
385
def companionDefs (parentTpt : Tree , defs : List [Tree ]) =
385
386
moduleDef(
386
387
ModuleDef (
387
- name .toTermName, Template (emptyConstructor, parentTpt :: Nil , EmptyValDef , defs))
388
+ className .toTermName, Template (emptyConstructor, parentTpt :: Nil , EmptyValDef , defs))
388
389
.withMods(companionMods | Synthetic ))
389
390
.withPos(cdef.pos).toList
390
391
@@ -443,7 +444,7 @@ object desugar {
443
444
else
444
445
// implicit wrapper is typechecked in same scope as constructor, so
445
446
// we can reuse the constructor parameters; no derived params are needed.
446
- DefDef (name .toTermName, constrTparams, constrVparamss, classTypeRef, creatorExpr)
447
+ DefDef (className .toTermName, constrTparams, constrVparamss, classTypeRef, creatorExpr)
447
448
.withMods(companionMods | Synthetic | Implicit )
448
449
.withPos(cdef.pos) :: Nil
449
450
@@ -460,6 +461,7 @@ object desugar {
460
461
val caseAccessor = if (isCaseClass) CaseAccessor else EmptyFlags
461
462
val vparamAccessors = derivedVparamss.flatten.map(_.withMods(originalVparams.next.mods | caseAccessor))
462
463
cpy.TypeDef (cdef)(
464
+ name = className,
463
465
rhs = cpy.Template (impl)(constr, parents1, self1,
464
466
tparamAccessors ::: vparamAccessors ::: normalizedBody ::: caseClassMeths),
465
467
tparams = Nil )
@@ -485,20 +487,21 @@ object desugar {
485
487
* <module> final class name$ extends parents { self: name.type => body }
486
488
*/
487
489
def moduleDef (mdef : ModuleDef )(implicit ctx : Context ): Tree = {
488
- val ModuleDef (name, tmpl) = mdef
490
+ val moduleName = checkNotReservedName(mdef).asTermName
491
+ val tmpl = mdef.impl
489
492
val mods = mdef.mods
490
493
if (mods is Package )
491
- PackageDef (Ident (name ), cpy.ModuleDef (mdef)(nme.PACKAGE , tmpl).withMods(mods &~ Package ) :: Nil )
494
+ PackageDef (Ident (moduleName ), cpy.ModuleDef (mdef)(nme.PACKAGE , tmpl).withMods(mods &~ Package ) :: Nil )
492
495
else {
493
- val clsName = name .moduleClassName
496
+ val clsName = moduleName .moduleClassName
494
497
val clsRef = Ident (clsName)
495
- val modul = ValDef (name , clsRef, New (clsRef, Nil ))
498
+ val modul = ValDef (moduleName , clsRef, New (clsRef, Nil ))
496
499
.withMods(mods | ModuleCreationFlags | mods.flags & AccessFlags )
497
500
.withPos(mdef.pos)
498
501
val ValDef (selfName, selfTpt, _) = tmpl.self
499
502
val selfMods = tmpl.self.mods
500
503
if (! selfTpt.isEmpty) ctx.error(ObjectMayNotHaveSelfType (mdef), tmpl.self.pos)
501
- val clsSelf = ValDef (selfName, SingletonTypeTree (Ident (name )), tmpl.self.rhs)
504
+ val clsSelf = ValDef (selfName, SingletonTypeTree (Ident (moduleName )), tmpl.self.rhs)
502
505
.withMods(selfMods)
503
506
.withPos(tmpl.self.pos orElse tmpl.pos.startPos)
504
507
val clsTmpl = cpy.Template (tmpl)(self = clsSelf, body = tmpl.body)
@@ -508,6 +511,19 @@ object desugar {
508
511
}
509
512
}
510
513
514
+ /** The name of `mdef`, after checking that it does not redefine a Scala core class.
515
+ * If it does redefine, issue an error and return a mangled name instead of the original one.
516
+ */
517
+ def checkNotReservedName (mdef : MemberDef )(implicit ctx : Context ): Name = {
518
+ val name = mdef.name
519
+ if (ctx.owner == defn.ScalaPackageClass && defn.reservedScalaClassNames.contains(name.toTypeName)) {
520
+ def kind = if (name.isTypeName) " class" else " object"
521
+ ctx.error(em " illegal redefinition of standard $kind $name" , mdef.pos)
522
+ name.errorName
523
+ }
524
+ else name
525
+ }
526
+
511
527
/** val p1, ..., pN: T = E
512
528
* ==>
513
529
* makePatDef[[val p1: T1 = E ]]; ...; makePatDef[[val pN: TN = E ]]
0 commit comments