From 1a6408c42928211d5d119317cc1aec4eb2481101 Mon Sep 17 00:00:00 2001 From: Paul Phillips Date: Fri, 6 Apr 2012 13:13:08 -0700 Subject: Flag performance and Name management. One leads to the other. Easing some more specific typing into Symbols. Getting a handle on when where and how people rename symbols to suit their fancies. --- .../scala/reflect/internal/Importers.scala | 2 +- .../scala/reflect/internal/SymbolCreations.scala | 3 +- src/compiler/scala/reflect/internal/Symbols.scala | 151 ++++++++++++++------- .../reflect/runtime/SynchronizedSymbols.scala | 9 +- src/compiler/scala/tools/nsc/ast/DocComments.scala | 3 +- .../scala/tools/nsc/transform/AddInterfaces.scala | 6 +- .../scala/tools/nsc/transform/LambdaLift.scala | 6 +- .../tools/nsc/transform/SpecializeTypes.scala | 15 +- .../scala/tools/nsc/typechecker/Contexts.scala | 2 +- .../tools/nsc/typechecker/MethodSynthesis.scala | 3 +- .../scala/tools/nsc/typechecker/Namers.scala | 20 ++- .../tools/nsc/typechecker/TypeDiagnostics.scala | 3 +- 12 files changed, 139 insertions(+), 84 deletions(-) (limited to 'src/compiler') diff --git a/src/compiler/scala/reflect/internal/Importers.scala b/src/compiler/scala/reflect/internal/Importers.scala index 5dcff804a8..c9336e8cf1 100644 --- a/src/compiler/scala/reflect/internal/Importers.scala +++ b/src/compiler/scala/reflect/internal/Importers.scala @@ -72,7 +72,7 @@ trait Importers { self: SymbolTable => symMap(x) = mysym if (sym.thisSym != sym) { mysym.typeOfThis = importType(sym.typeOfThis) - mysym.thisSym.name = importName(sym.thisSym.name) + mysym.thisSym setName importName(sym.thisSym.name) } mysym case x: from.TypeSymbol => diff --git a/src/compiler/scala/reflect/internal/SymbolCreations.scala b/src/compiler/scala/reflect/internal/SymbolCreations.scala index 62fee9d7f3..77c4ee27c2 100644 --- a/src/compiler/scala/reflect/internal/SymbolCreations.scala +++ b/src/compiler/scala/reflect/internal/SymbolCreations.scala @@ -28,8 +28,9 @@ trait SymbolCreations { */ trait SymbolCreatorInterface { // Fallbacks; more precise creators should normally be called. - protected def createTypeSymbol(name: TypeName, pos: Position, newFlags: Long): TypeSymbol protected def createTermSymbol(name: TermName, pos: Position, newFlags: Long): TermSymbol + // This in fact does not exist anymore in the interests of better typed TypeSymbols. + // protected def createTypeSymbol(name: TypeName, pos: Position, newFlags: Long): TypeSymbol // I believe all but rogue TypeSymbols are one of: ClassSymbol, AbstractTypeSymbol, AliasTypeSymbol, or TypeSkolem. protected def createAbstractTypeSymbol(name: TypeName, pos: Position, newFlags: Long): AbstractTypeSymbol diff --git a/src/compiler/scala/reflect/internal/Symbols.scala b/src/compiler/scala/reflect/internal/Symbols.scala index 6666a49491..a30714f113 100644 --- a/src/compiler/scala/reflect/internal/Symbols.scala +++ b/src/compiler/scala/reflect/internal/Symbols.scala @@ -157,12 +157,22 @@ trait Symbols extends api.Symbols { self: SymbolTable => type AccessBoundaryType = Symbol type AnnotationType = AnnotationInfo + // TODO - don't allow names to be renamed in this unstructured a fashion. + // Rename as little as possible. Enforce invariants on all renames. + type NameType >: Null <: Name + type TypeOfClonedSymbol >: Null <: Symbol { type NameType = Symbol.this.NameType } + + // Abstract here so TypeSymbol and TermSymbol can have a private[this] field + // with the proper specific type. + def rawname: NameType + def name: NameType + def name_=(n: NameType): Unit + def asNameType(n: Name): NameType + private[this] var _rawowner = initOwner // Syncnote: need not be protected, as only assignment happens in owner_=, which is not exposed to api - private[this] var _rawname = initName private[this] var _rawflags: Long = _ def rawowner = _rawowner - def rawname = _rawname def rawflags = _rawflags private var rawpos = initPos @@ -178,6 +188,18 @@ trait Symbols extends api.Symbols { self: SymbolTable => def pos = rawpos def setPos(pos: Position): this.type = { this.rawpos = pos; this } + def setName(name: Name): this.type = { this.name = asNameType(name) ; this } + + // Update the surrounding scopes + protected[this] def changeNameInOwners(name: Name) { + if (owner.isClass) { + var ifs = owner.infos + while (ifs != null) { + ifs.info.decls.rehash(this, name) + ifs = ifs.prev + } + } + } /** !!! The logic after "hasFlag" is far too opaque to be unexplained. * I'm guessing it's attempting to compensate for flag overloading, @@ -236,8 +258,9 @@ trait Symbols extends api.Symbols { self: SymbolTable => newModule(name, pos, PackageFlags | newFlags) } - final def newThisSym(pos: Position) = - newTermSymbol(nme.this_, pos, SYNTHETIC) + final def newThisSym(name: TermName = nme.this_, pos: Position = NoPosition) = + newTermSymbol(name, pos, SYNTHETIC) + final def newImport(pos: Position) = newTermSymbol(nme.IMPORT, pos) @@ -385,6 +408,18 @@ trait Symbols extends api.Symbols { self: SymbolTable => case x: TermName => newErrorValue(x) } + /** To overcome the crazy challenge of more specific types appearing + * in incoming positions. Don't need this much. + */ + def asTypeSymbol: TypeSymbol = this match { + case x: TypeSymbol => x + case x => throw new FatalError(this + " is not a TypeSymbol") + } + def asTermSymbol: TermSymbol = this match { + case x: TermSymbol => x + case x => throw new FatalError(this + " is not a TermSymbol") + } + @deprecated("Use the other signature", "2.10.0") def newClass(pos: Position, name: TypeName): Symbol = newClass(name, pos) @deprecated("Use the other signature", "2.10.0") @@ -913,23 +948,6 @@ trait Symbols extends api.Symbols { self: SymbolTable => // ------ name attribute -------------------------------------------------------------- - def name: Name = rawname - - // TODO - don't allow names to be renamed in this unstructured a fashion. - // Rename as little as possible. Enforce invariants on all renames. - def name_=(name: Name) { - if (name != rawname) { - if (owner.isClass) { - var ifs = owner.infos - while (ifs != null) { - ifs.info.decls.rehash(this, name) - ifs = ifs.prev - } - } - _rawname = name - } - } - /** If this symbol has an expanded name, its original name, otherwise its name itself. * @see expandName */ @@ -991,8 +1009,6 @@ trait Symbols extends api.Symbols { self: SymbolTable => /** * Symbol creation implementations. */ - protected def createTypeSymbol(name: TypeName, pos: Position, newFlags: Long): TypeSymbol = - new TypeSymbol(this, pos, name) { } initFlags newFlags protected def createAbstractTypeSymbol(name: TypeName, pos: Position, newFlags: Long): AbstractTypeSymbol = new AbstractTypeSymbol(this, pos, name) initFlags newFlags @@ -1496,15 +1512,15 @@ trait Symbols extends api.Symbols { self: SymbolTable => // ------ cloneing ------------------------------------------------------------------- /** A clone of this symbol. */ - final def cloneSymbol: Symbol = + final def cloneSymbol: TypeOfClonedSymbol = cloneSymbol(owner) /** A clone of this symbol, but with given owner. */ - final def cloneSymbol(newOwner: Symbol): Symbol = + final def cloneSymbol(newOwner: Symbol): TypeOfClonedSymbol = cloneSymbol(newOwner, _rawflags) - final def cloneSymbol(newOwner: Symbol, newFlags: Long): Symbol = - cloneSymbol(newOwner, newFlags, nme.NO_NAME) - final def cloneSymbol(newOwner: Symbol, newFlags: Long, newName: Name): Symbol = { + final def cloneSymbol(newOwner: Symbol, newFlags: Long): TypeOfClonedSymbol = + cloneSymbol(newOwner, newFlags, null) + final def cloneSymbol(newOwner: Symbol, newFlags: Long, newName: Name): TypeOfClonedSymbol = { val clone = cloneSymbolImpl(newOwner, newFlags) ( clone setPrivateWithin privateWithin @@ -1513,14 +1529,14 @@ trait Symbols extends api.Symbols { self: SymbolTable => ) if (clone.thisSym != clone) clone.typeOfThis = (clone.typeOfThis cloneInfo clone) - if (newName != nme.NO_NAME) - clone.name = newName + if (newName ne null) + clone setName asNameType(newName) clone } /** Internal method to clone a symbol's implementation with the given flags and no info. */ - def cloneSymbolImpl(owner: Symbol, newFlags: Long): Symbol + def cloneSymbolImpl(owner: Symbol, newFlags: Long): TypeOfClonedSymbol // ------ access to related symbols -------------------------------------------------- @@ -2200,8 +2216,21 @@ trait Symbols extends api.Symbols { self: SymbolTable => private[this] var _referenced: Symbol = NoSymbol privateWithin = NoSymbol + final type NameType = TermName + type TypeOfClonedSymbol = TermSymbol + + private[this] var _rawname: TermName = initName + def rawname = _rawname + def name = _rawname + def name_=(name: TermName) { + if (name != rawname) { + changeNameInOwners(name) + _rawname = name + } + } + final def asNameType(n: Name) = n.toTermName + final override def isTerm = true - override def name: TermName = rawname.toTermName override def companionSymbol: Symbol = companionClass override def moduleClass = if (isModule) referenced else NoSymbol @@ -2232,7 +2261,7 @@ trait Symbols extends api.Symbols { self: SymbolTable => def existentialBound = singletonBounds(this.tpe) - def cloneSymbolImpl(owner: Symbol, newFlags: Long): Symbol = + def cloneSymbolImpl(owner: Symbol, newFlags: Long): TermSymbol = owner.newTermSymbol(name, pos, newFlags).copyAttrsFrom(this) def copyAttrsFrom(original: TermSymbol): this.type = { @@ -2328,7 +2357,6 @@ trait Symbols extends api.Symbols { self: SymbolTable => class ModuleSymbol protected[Symbols] (initOwner: Symbol, initPos: Position, initName: TermName) extends TermSymbol(initOwner, initPos, initName) with DistinguishingFlag { def distinguishingFlag = MODULE - private var flatname: TermName = null override def isModule = true @@ -2347,7 +2375,7 @@ trait Symbols extends api.Symbols { self: SymbolTable => flatname } - else rawname.toTermName + else rawname ) } @@ -2400,13 +2428,19 @@ trait Symbols extends api.Symbols { self: SymbolTable => class AliasTypeSymbol protected[Symbols] (initOwner: Symbol, initPos: Position, initName: TypeName) extends TypeSymbol(initOwner, initPos, initName) { + type TypeOfClonedSymbol = TypeSymbol final override def isAliasType = true + override def cloneSymbolImpl(owner: Symbol, newFlags: Long): TypeSymbol = + owner.newNonClassSymbol(name, pos, newFlags) } class AbstractTypeSymbol protected[Symbols] (initOwner: Symbol, initPos: Position, initName: TypeName) extends TypeSymbol(initOwner, initPos, initName) { + type TypeOfClonedSymbol = TypeSymbol final override def isAbstractType = true override def existentialBound = this.info + override def cloneSymbolImpl(owner: Symbol, newFlags: Long): TypeSymbol = + owner.newNonClassSymbol(name, pos, newFlags) } /** A class of type symbols. Alias and abstract types are direct instances @@ -2415,6 +2449,15 @@ trait Symbols extends api.Symbols { self: SymbolTable => abstract class TypeSymbol protected[Symbols] (initOwner: Symbol, initPos: Position, initName: TypeName) extends Symbol(initOwner, initPos, initName) { privateWithin = NoSymbol + private[this] var _rawname: TypeName = initName + + final type NameType = TypeName + type TypeOfClonedSymbol >: Null <: TypeSymbol + // cloneSymbolImpl still abstract in TypeSymbol. + + def rawname = _rawname + def name = _rawname + final def asNameType(n: Name) = n.toTypeName final override def isType = true override def isNonClassType = true @@ -2447,7 +2490,16 @@ trait Symbols extends api.Symbols { self: SymbolTable => // a type symbol bound by an existential type, for instance the T in // List[T] forSome { type T } - override def name: TypeName = super.name.toTypeName + // TODO - don't allow names to be renamed in this unstructured a fashion. + // Rename as little as possible. Enforce invariants on all renames. + def name_=(name: TypeName) { + if (name != rawname) { + changeNameInOwners(name) + _rawname = name + } + } + + private def newPrefix = if (this hasFlag EXISTENTIAL | PARAM) NoPrefix else owner.thisType private def newTypeRef(targs: List[Type]) = typeRef(newPrefix, this, targs) @@ -2542,10 +2594,6 @@ trait Symbols extends api.Symbols { self: SymbolTable => } } - /** Default implementation. */ - def cloneSymbolImpl(owner: Symbol, newFlags: Long): Symbol = - owner.newNonClassSymbol(name, pos, newFlags) - incCounter(typeSymbolCount) } @@ -2564,6 +2612,7 @@ trait Symbols extends api.Symbols { self: SymbolTable => */ class TypeSkolem protected[Symbols] (initOwner: Symbol, initPos: Position, initName: TypeName, origin: AnyRef) extends TypeSymbol(initOwner, initPos, initName) { + type TypeOfClonedSymbol = TypeSkolem /** The skolemization level in place when the skolem was constructed */ val level = skolemizationLevel @@ -2589,7 +2638,7 @@ trait Symbols extends api.Symbols { self: SymbolTable => //@M! (not deSkolemize.typeParams!!), also can't leave superclass definition: use info, not rawInfo override def typeParams = info.typeParams - override def cloneSymbolImpl(owner: Symbol, newFlags: Long): Symbol = + override def cloneSymbolImpl(owner: Symbol, newFlags: Long): TypeSkolem = owner.newTypeSkolemSymbol(name, origin, pos, newFlags) override def nameString: String = @@ -2600,6 +2649,8 @@ trait Symbols extends api.Symbols { self: SymbolTable => /** A class for class symbols */ class ClassSymbol protected[Symbols] (initOwner: Symbol, initPos: Position, initName: TypeName) extends TypeSymbol(initOwner, initPos, initName) { + type TypeOfClonedSymbol = ClassSymbol + private[this] var flatname: TypeName = _ private[this] var source: AbstractFileType = _ private[this] var thissym: Symbol = this @@ -2737,7 +2788,7 @@ trait Symbols extends api.Symbols { self: SymbolTable => flatname } - else rawname.toTypeName + else rawname ) /** A symbol carrying the self type of the class as its type */ @@ -2745,14 +2796,14 @@ trait Symbols extends api.Symbols { self: SymbolTable => /** Sets the self type of the class */ override def typeOfThis_=(tp: Type) { - thissym = newThisSym(pos).setInfo(tp) + thissym = newThisSym(nme.this_, pos).setInfo(tp) } override def cloneSymbolImpl(owner: Symbol, newFlags: Long): ClassSymbol = { val clone = owner.newClassSymbol(name, pos, newFlags) if (thisSym != this) { clone.typeOfThis = typeOfThis - clone.thisSym.name = thisSym.name + clone.thisSym setName thisSym.name } clone } @@ -2813,7 +2864,7 @@ trait Symbols extends api.Symbols { self: SymbolTable => class RefinementClassSymbol protected[Symbols] (owner0: Symbol, pos0: Position) extends ClassSymbol(owner0, pos0, tpnme.REFINE_CLASS_NAME) { - override def name_=(name: Name) { + override def name_=(name: TypeName) { assert(false, "Cannot set name of RefinementClassSymbol to " + name) super.name_=(name) } @@ -2842,6 +2893,14 @@ trait Symbols extends api.Symbols { self: SymbolTable => /** An object representing a missing symbol */ class NoSymbol protected[Symbols]() extends Symbol(null, NoPosition, nme.NO_NAME) { + final type NameType = TermName + type TypeOfClonedSymbol = NoSymbol + + def asNameType(n: Name) = n.toTermName + def rawname = nme.NO_NAME + def name = nme.NO_NAME + def name_=(n: TermName) = abort("Cannot set name to " + n) + synchronized { setInfo(NoType) privateWithin = this @@ -2876,7 +2935,7 @@ trait Symbols extends api.Symbols { self: SymbolTable => override def rawInfo: Type = NoType protected def doCookJavaRawInfo() {} override def accessBoundary(base: Symbol): Symbol = RootClass - def cloneSymbolImpl(owner: Symbol, newFlags: Long): Symbol = abort("NoSymbol.clone()") + def cloneSymbolImpl(owner: Symbol, newFlags: Long) = abort("NoSymbol.clone()") override def originalEnclosingMethod = this override def owner: Symbol = diff --git a/src/compiler/scala/reflect/runtime/SynchronizedSymbols.scala b/src/compiler/scala/reflect/runtime/SynchronizedSymbols.scala index 6d8aa8d1db..2956bc8a21 100644 --- a/src/compiler/scala/reflect/runtime/SynchronizedSymbols.scala +++ b/src/compiler/scala/reflect/runtime/SynchronizedSymbols.scala @@ -22,11 +22,9 @@ trait SynchronizedSymbols extends internal.Symbols { self: SymbolTable => trait SynchronizedSymbol extends Symbol { override def rawowner = synchronized { super.rawowner } - override def rawname = synchronized { super.rawname } override def rawflags = synchronized { super.rawflags } override def rawflags_=(x: Long) = synchronized { super.rawflags_=(x) } - override def name_=(x: Name) = synchronized { super.name_=(x) } override def owner_=(owner: Symbol) = synchronized { super.owner_=(owner) } override def validTo = synchronized { super.validTo } @@ -55,9 +53,6 @@ trait SynchronizedSymbols extends internal.Symbols { self: SymbolTable => // ------ creators ------------------------------------------------------------------- - override protected def createTypeSymbol(name: TypeName, pos: Position, newFlags: Long): TypeSymbol = - new TypeSymbol(this, pos, name) with SynchronizedTypeSymbol initFlags newFlags - override protected def createAbstractTypeSymbol(name: TypeName, pos: Position, newFlags: Long): AbstractTypeSymbol = new AbstractTypeSymbol(this, pos, name) with SynchronizedTypeSymbol initFlags newFlags @@ -99,6 +94,8 @@ trait SynchronizedSymbols extends internal.Symbols { self: SymbolTable => // ------- subclasses --------------------------------------------------------------------- trait SynchronizedTermSymbol extends TermSymbol with SynchronizedSymbol { + override def name_=(x: TermName) = synchronized { super.name_=(x) } + override def rawname = synchronized { super.rawname } override def referenced: Symbol = synchronized { super.referenced } override def referenced_=(x: Symbol) = synchronized { super.referenced_=(x) } } @@ -108,6 +105,8 @@ trait SynchronizedSymbols extends internal.Symbols { self: SymbolTable => } trait SynchronizedTypeSymbol extends TypeSymbol with SynchronizedSymbol { + override def name_=(x: TypeName) = synchronized { super.name_=(x) } + override def rawname = synchronized { super.rawname } override def typeConstructor: Type = synchronized { super.typeConstructor } override def tpe: Type = synchronized { super.tpe } } diff --git a/src/compiler/scala/tools/nsc/ast/DocComments.scala b/src/compiler/scala/tools/nsc/ast/DocComments.scala index 4c7083a51f..456e7eae9e 100755 --- a/src/compiler/scala/tools/nsc/ast/DocComments.scala +++ b/src/compiler/scala/tools/nsc/ast/DocComments.scala @@ -495,8 +495,7 @@ trait DocComments { self: Global => val tpe = getType(repl.trim) if (tpe != NoType) tpe else { - val alias1 = alias.cloneSymbol(definitions.RootClass) - alias1.name = newTypeName(repl) + val alias1 = alias.cloneSymbol(definitions.RootClass, alias.rawflags, newTypeName(repl)) typeRef(NoPrefix, alias1, Nil) } case None => diff --git a/src/compiler/scala/tools/nsc/transform/AddInterfaces.scala b/src/compiler/scala/tools/nsc/transform/AddInterfaces.scala index 34bad05e1f..e981910bdb 100644 --- a/src/compiler/scala/tools/nsc/transform/AddInterfaces.scala +++ b/src/compiler/scala/tools/nsc/transform/AddInterfaces.scala @@ -66,9 +66,10 @@ abstract class AddInterfaces extends InfoTransform { self: Erasure => /** Return the implementation class of a trait; create a new one of one does not yet exist */ def implClass(iface: Symbol): Symbol = { - iface.info def implClassFlags = iface.flags & ~(INTERFACE | lateINTERFACE) | IMPLCLASS + iface.info + implClassMap.getOrElse(iface, { atPhase(implClassPhase) { if (iface.implClass ne NoSymbol) @@ -98,8 +99,7 @@ abstract class AddInterfaces extends InfoTransform { self: Erasure => else log("not unlinking existing " + impl + " as the impl class is not visible on the classpath.") } if (impl == NoSymbol) { - impl = iface.cloneSymbolImpl(iface.owner, implClassFlags) - impl.name = implName + impl = iface.cloneSymbolImpl(iface.owner, implClassFlags) setName implName impl.sourceFile = iface.sourceFile if (iface.owner.isClass) iface.owner.info.decls enter impl diff --git a/src/compiler/scala/tools/nsc/transform/LambdaLift.scala b/src/compiler/scala/tools/nsc/transform/LambdaLift.scala index 13ca8e55bc..36571ceb7f 100644 --- a/src/compiler/scala/tools/nsc/transform/LambdaLift.scala +++ b/src/compiler/scala/tools/nsc/transform/LambdaLift.scala @@ -229,10 +229,10 @@ abstract class LambdaLift extends InfoTransform { sym.owner.name + nme.NAME_JOIN_STRING else "" ) - sym.name = + sym setName ( if (sym.name.isTypeName) unit.freshTypeName(base) else unit.freshTermName(base) - + ) debuglog("renaming in %s: %s => %s".format(sym.owner.fullLocationString, originalName, sym.name)) } @@ -241,7 +241,7 @@ abstract class LambdaLift extends InfoTransform { def renameTrait(traitSym: Symbol, implSym: Symbol) { val originalImplName = implSym.name renameSym(traitSym) - implSym.name = nme.implClassName(traitSym.name) + implSym setName nme.implClassName(traitSym.name) debuglog("renaming impl class in step with %s: %s => %s".format(traitSym, originalImplName, implSym.name)) } diff --git a/src/compiler/scala/tools/nsc/transform/SpecializeTypes.scala b/src/compiler/scala/tools/nsc/transform/SpecializeTypes.scala index 1afa1dbf58..51da933312 100644 --- a/src/compiler/scala/tools/nsc/transform/SpecializeTypes.scala +++ b/src/compiler/scala/tools/nsc/transform/SpecializeTypes.scala @@ -513,8 +513,8 @@ abstract class SpecializeTypes extends InfoTransform with TypingTransformers { val sClass = clazz.owner.newClass(clazzName, clazz.pos, (clazz.flags | SPECIALIZED) & ~CASE) - def cloneInSpecializedClass(member: Symbol, flagFn: Long => Long) = - member.cloneSymbol(sClass, flagFn(member.flags | SPECIALIZED)) + def cloneInSpecializedClass(member: Symbol, flagFn: Long => Long, newName: Name = null) = + member.cloneSymbol(sClass, flagFn(member.flags | SPECIALIZED), newName) sClass.sourceFile = clazz.sourceFile currentRun.symSource(sClass) = clazz.sourceFile // needed later on by mixin @@ -726,7 +726,7 @@ abstract class SpecializeTypes extends InfoTransform with TypingTransformers { else if (m.isClass) { val specClass: Symbol = cloneInSpecializedClass(m, x => x) typeEnv(specClass) = fullEnv - specClass.name = specializedName(specClass, fullEnv).toTypeName + specClass setName specializedName(specClass, fullEnv).toTypeName enterMember(specClass) debuglog("entered specialized class " + specClass.fullName) info(specClass) = SpecializedInnerClass(m, fullEnv) @@ -804,7 +804,7 @@ abstract class SpecializeTypes extends InfoTransform with TypingTransformers { val env = mapAnyRefsInSpecSym(env0, sym, specMember) val (keys, vals) = env.toList.unzip - specMember.name = specializedName(sym, env) + specMember setName specializedName(sym, env) // debuglog("%s normalizes to %s%s".format(sym, specMember, // if (tps.isEmpty) "" else " with params " + tps.mkString(", "))) @@ -882,10 +882,11 @@ abstract class SpecializeTypes extends InfoTransform with TypingTransformers { /** Return the specialized overload of `m`, in the given environment. */ private def specializedOverload(owner: Symbol, sym: Symbol, env: TypeEnv): Symbol = { + val newFlags = (sym.flags | SPECIALIZED) & ~(DEFERRED | CASEACCESSOR | ACCESSOR | LAZY) // this method properly duplicates the symbol's info - val specMember = sym.cloneSymbol(owner, (sym.flags | SPECIALIZED) & ~(DEFERRED | CASEACCESSOR | ACCESSOR | LAZY)) - specMember.name = specializedName(sym, env) - specMember modifyInfo (info => subst(env, info.asSeenFrom(owner.thisType, sym.owner))) + ( sym.cloneSymbol(owner, newFlags, specializedName(sym, env)) + modifyInfo (info => subst(env, info.asSeenFrom(owner.thisType, sym.owner))) + ) } /** For each method m that overrides an inherited method m', add a special diff --git a/src/compiler/scala/tools/nsc/typechecker/Contexts.scala b/src/compiler/scala/tools/nsc/typechecker/Contexts.scala index a1ba8a2982..9b1f395ad0 100644 --- a/src/compiler/scala/tools/nsc/typechecker/Contexts.scala +++ b/src/compiler/scala/tools/nsc/typechecker/Contexts.scala @@ -664,7 +664,7 @@ trait Contexts { self: Analyzer => case List(ImportSelector(nme.WILDCARD, _, _, _)) => List(sym) case ImportSelector(from, _, to, _) :: _ if from == sym.name => if (to == nme.WILDCARD) List() - else { val sym1 = sym.cloneSymbol; sym1.name = to; List(sym1) } + else List(sym.cloneSymbol(sym.owner, sym.rawflags, to)) case _ :: rest => transformImport(rest, sym) } diff --git a/src/compiler/scala/tools/nsc/typechecker/MethodSynthesis.scala b/src/compiler/scala/tools/nsc/typechecker/MethodSynthesis.scala index 04341fea25..82ffc3fd9e 100644 --- a/src/compiler/scala/tools/nsc/typechecker/MethodSynthesis.scala +++ b/src/compiler/scala/tools/nsc/typechecker/MethodSynthesis.scala @@ -96,8 +96,7 @@ trait MethodSynthesis { finishMethod(m setInfoAndEnter infoFn(m), f) } private def cloneInternal(original: Symbol, f: Symbol => Tree, name: Name): Tree = { - val m = original.cloneSymbol(clazz, newMethodFlags(original)) setPos clazz.pos.focus - m.name = name + val m = original.cloneSymbol(clazz, newMethodFlags(original), name) setPos clazz.pos.focus finishMethod(clazz.info.decls enter m, f) } diff --git a/src/compiler/scala/tools/nsc/typechecker/Namers.scala b/src/compiler/scala/tools/nsc/typechecker/Namers.scala index ed17d6efa7..2539091966 100644 --- a/src/compiler/scala/tools/nsc/typechecker/Namers.scala +++ b/src/compiler/scala/tools/nsc/typechecker/Namers.scala @@ -831,19 +831,17 @@ trait Namers extends MethodSynthesis { if (!hasType) tpt defineType NoType - if (hasType || hasName) { - owner.typeOfThis = - if (hasType) selfTypeCompleter(tpt) - else owner.tpe - } val sym = ( - if (hasType) owner.thisSym setPos self.pos - else if (hasName) owner.thisSym - else owner.newThisSym(self.pos) setInfo owner.tpe + if (hasType || hasName) { + owner.typeOfThis = if (hasType) selfTypeCompleter(tpt) else owner.tpe + val selfSym = owner.thisSym setPos self.pos + if (hasName) selfSym setName name else selfSym + } + else { + val symName = if (name != nme.WILDCARD) name else nme.this_ + owner.newThisSym(symName, owner.pos) setInfo owner.tpe + } ) - if (hasName) - sym.name = name - self.symbol = context.scope enter sym } diff --git a/src/compiler/scala/tools/nsc/typechecker/TypeDiagnostics.scala b/src/compiler/scala/tools/nsc/typechecker/TypeDiagnostics.scala index 6efa595d99..3233b7b07c 100644 --- a/src/compiler/scala/tools/nsc/typechecker/TypeDiagnostics.scala +++ b/src/compiler/scala/tools/nsc/typechecker/TypeDiagnostics.scala @@ -270,8 +270,7 @@ trait TypeDiagnostics { private val savedName = sym.name def restoreName() = sym.name = savedName def isAltered = sym.name != savedName - def modifyName(f: String => String) = - sym.name = newTypeName(f(sym.name.toString)) + def modifyName(f: String => String) = sym setName newTypeName(f(sym.name.toString)) /** Prepend java.lang, scala., or Predef. if this type originated * in one of those. -- cgit v1.2.3