From b2fbae789e336456381cd53f80802621df48218a Mon Sep 17 00:00:00 2001 From: Miles Sabin Date: Sun, 25 Oct 2009 17:12:45 +0000 Subject: Add positions to AnnotationInfo for use by IDEs... Add positions to AnnotationInfo for use by IDEs and other tools. --- .../scala/tools/nsc/backend/jvm/GenJVM.scala | 22 +++++++++++----------- .../scala/tools/nsc/backend/msil/GenMSIL.scala | 6 +++--- src/compiler/scala/tools/nsc/doc/ModelToXML.scala | 2 +- .../tools/nsc/interactive/RangePositions.scala | 7 +++++++ .../scala/tools/nsc/symtab/AnnotationInfos.scala | 4 ++-- src/compiler/scala/tools/nsc/symtab/Symbols.scala | 2 +- src/compiler/scala/tools/nsc/symtab/Types.scala | 6 +++--- .../nsc/symtab/classfile/ClassfileParser.scala | 4 ++-- .../scala/tools/nsc/symtab/classfile/Pickler.scala | 10 +++++----- .../tools/nsc/symtab/classfile/UnPickler.scala | 2 +- .../scala/tools/nsc/transform/CleanUp.scala | 6 +++--- src/compiler/scala/tools/nsc/transform/Mixin.scala | 2 +- .../tools/nsc/transform/SpecializeTypes.scala | 2 +- .../scala/tools/nsc/typechecker/Namers.scala | 4 ++-- .../tools/nsc/typechecker/SyntheticMethods.scala | 3 ++- .../scala/tools/nsc/typechecker/Typers.scala | 8 ++++---- 16 files changed, 49 insertions(+), 41 deletions(-) (limited to 'src/compiler') diff --git a/src/compiler/scala/tools/nsc/backend/jvm/GenJVM.scala b/src/compiler/scala/tools/nsc/backend/jvm/GenJVM.scala index 415a56712a..d66117c034 100644 --- a/src/compiler/scala/tools/nsc/backend/jvm/GenJVM.scala +++ b/src/compiler/scala/tools/nsc/backend/jvm/GenJVM.scala @@ -171,13 +171,13 @@ abstract class GenJVM extends SubComponent { parents = definitions.ObjectClass.tpe :: parents; for (annot <- c.symbol.annotations) annot match { - case AnnotationInfo(tp, _, _) if tp.typeSymbol == SerializableAttr => + case AnnotationInfo(tp, _, _, _) if tp.typeSymbol == SerializableAttr => parents = parents ::: List(definitions.SerializableClass.tpe) - case AnnotationInfo(tp, _, _) if tp.typeSymbol == CloneableAttr => + case AnnotationInfo(tp, _, _, _) if tp.typeSymbol == CloneableAttr => parents = parents ::: List(CloneableClass.tpe) - case AnnotationInfo(tp, Literal(const) :: _, _) if tp.typeSymbol == SerialVersionUID => + case AnnotationInfo(tp, Literal(const) :: _, _, _) if tp.typeSymbol == SerialVersionUID => serialVUID = Some(const.longValue) - case AnnotationInfo(tp, _, _) if tp.typeSymbol == RemoteAttr => + case AnnotationInfo(tp, _, _, _) if tp.typeSymbol == RemoteAttr => parents = parents ::: List(RemoteInterface.tpe) remoteClass = true case _ => () @@ -330,7 +330,7 @@ abstract class GenJVM extends SubComponent { // put some radom value; the actual number is determined at the end buf.putShort(0xbaba.toShort) - for (AnnotationInfo(tp, List(exc), _) <- excs.removeDuplicates if tp.typeSymbol == ThrowsAttr) { + for (AnnotationInfo(tp, List(exc), _, _) <- excs.removeDuplicates if tp.typeSymbol == ThrowsAttr) { val Literal(const) = exc buf.putShort( cpool.addClass( @@ -402,7 +402,7 @@ abstract class GenJVM extends SubComponent { } def emitAnnotation(annotInfo: AnnotationInfo) { - val AnnotationInfo(typ, args, assocs) = annotInfo + val AnnotationInfo(typ, args, assocs, _) = annotInfo val jtype = javaType(typ) buf.putShort(cpool.addUtf8(jtype.getSignature()).toShort) assert(args.isEmpty, args.toString) @@ -537,9 +537,9 @@ abstract class GenJVM extends SubComponent { var attributes = 0 f.symbol.annotations foreach { a => a match { - case AnnotationInfo(tp, _, _) if tp.typeSymbol == TransientAtt => + case AnnotationInfo(tp, _, _, _) if tp.typeSymbol == TransientAtt => attributes = attributes | JAccessFlags.ACC_TRANSIENT - case AnnotationInfo(tp, _, _) if tp.typeSymbol == VolatileAttr => + case AnnotationInfo(tp, _, _, _) if tp.typeSymbol == VolatileAttr => attributes = attributes | JAccessFlags.ACC_VOLATILE case _ => (); }} @@ -622,7 +622,7 @@ abstract class GenJVM extends SubComponent { private def addRemoteException(jmethod: JMethod, meth: Symbol) { def isRemoteThrows(ainfo: AnnotationInfo) = ainfo match { - case AnnotationInfo(tp, List(arg), _) if tp.typeSymbol == ThrowsAttr => + case AnnotationInfo(tp, List(arg), _, _) if tp.typeSymbol == ThrowsAttr => arg match { case Literal(Constant(tpe: Type)) if tpe.typeSymbol == RemoteException.typeSymbol => true case _ => false @@ -633,7 +633,7 @@ abstract class GenJVM extends SubComponent { if (remoteClass || (meth.hasAnnotation(RemoteAttr) && jmethod.isPublic())) { val c = Constant(RemoteException) - val ainfo = AnnotationInfo(ThrowsAttr.tpe, List(Literal(c).setType(c.tpe)), List()) + val ainfo = AnnotationInfo(ThrowsAttr.tpe, List(Literal(c).setType(c.tpe)), List(), NoPosition) if (!meth.annotations.exists(isRemoteThrows)) { meth.addAnnotation(ainfo) } @@ -646,7 +646,7 @@ abstract class GenJVM extends SubComponent { */ private def splitAnnotations(annotations: List[AnnotationInfo], annotSym: Symbol): (List[AnnotationInfo], List[AnnotationInfo]) = { annotations.partition { a => a match { - case AnnotationInfo(tp, _, _) if tp.typeSymbol == annotSym => true + case AnnotationInfo(tp, _, _, _) if tp.typeSymbol == annotSym => true case _ => false }} } diff --git a/src/compiler/scala/tools/nsc/backend/msil/GenMSIL.scala b/src/compiler/scala/tools/nsc/backend/msil/GenMSIL.scala index 2163940ea5..1235ce0405 100644 --- a/src/compiler/scala/tools/nsc/backend/msil/GenMSIL.scala +++ b/src/compiler/scala/tools/nsc/backend/msil/GenMSIL.scala @@ -1858,7 +1858,7 @@ abstract class GenMSIL extends SubComponent { mf = mf | (if (sym isFinal) TypeAttributes.Sealed else 0) sym.annotations foreach { a => a match { - case AnnotationInfo(SerializableAttr, _, _) => + case AnnotationInfo(SerializableAttr, _, _, _) => // TODO: add the Serializable TypeAttribute also if the annotation // System.SerializableAttribute is present (.net annotation, not scala) // Best way to do it: compare with @@ -1908,7 +1908,7 @@ abstract class GenMSIL extends SubComponent { // TODO: add this annotation also if the class has the custom attribute // System.NotSerializedAttribute sym.annotations.foreach( a => a match { - case AnnotationInfo(TransientAtt, _, _) => + case AnnotationInfo(TransientAtt, _, _, _) => mf = mf | FieldAttributes.NotSerialized case _ => () }) @@ -2123,7 +2123,7 @@ abstract class GenMSIL extends SubComponent { private def isCloneable(sym: Symbol): Boolean = { !sym.annotations.forall( a => a match { - case AnnotationInfo(CloneableAttr, _, _) => false + case AnnotationInfo(CloneableAttr, _, _, _) => false case _ => true }) } diff --git a/src/compiler/scala/tools/nsc/doc/ModelToXML.scala b/src/compiler/scala/tools/nsc/doc/ModelToXML.scala index 19d67ab2fd..75f85bf528 100644 --- a/src/compiler/scala/tools/nsc/doc/ModelToXML.scala +++ b/src/compiler/scala/tools/nsc/doc/ModelToXML.scala @@ -349,7 +349,7 @@ trait ModelToXML extends ModelExtractor { def attrsFor(entity: Entity)(implicit from: Frame): NodeSeq = { def attrFor(attr: AnnotationInfo): Node = { val buf = new StringBuilder - val AnnotationInfo(tpe, args, nvPairs) = attr + val AnnotationInfo(tpe, args, nvPairs, _) = attr val name = link(decode(tpe.typeSymbol)) if (!args.isEmpty) buf.append(args.mkString("(", ",", ")")) diff --git a/src/compiler/scala/tools/nsc/interactive/RangePositions.scala b/src/compiler/scala/tools/nsc/interactive/RangePositions.scala index 294909c83b..2e6041f4c4 100644 --- a/src/compiler/scala/tools/nsc/interactive/RangePositions.scala +++ b/src/compiler/scala/tools/nsc/interactive/RangePositions.scala @@ -257,6 +257,13 @@ self: scala.tools.nsc.Global => if (t.pos includes pos) { if (!t.pos.isTransparent) last = t super.traverse(t) + } else if (t.symbol != null) { + for(annot <- t.symbol.annotations if !annot.pos.isTransparent) { + last = Annotated(TypeTree(annot.atp) setPos annot.pos, t) + last.setType(annot.atp) + last.setPos(annot.pos) + traverseTrees(annot.args) + } } } } diff --git a/src/compiler/scala/tools/nsc/symtab/AnnotationInfos.scala b/src/compiler/scala/tools/nsc/symtab/AnnotationInfos.scala index 13b3f752f5..211e9ea6aa 100644 --- a/src/compiler/scala/tools/nsc/symtab/AnnotationInfos.scala +++ b/src/compiler/scala/tools/nsc/symtab/AnnotationInfos.scala @@ -75,7 +75,7 @@ trait AnnotationInfos { *

*/ case class AnnotationInfo(atp: Type, args: List[Tree], - assocs: List[(Name, ClassfileAnnotArg)]) + assocs: List[(Name, ClassfileAnnotArg)], pos : Position) extends AnnotationInfoBase { // Classfile annot: args empty. Scala annot: assocs empty. @@ -95,7 +95,7 @@ trait AnnotationInfos { /** Change all ident's with Symbol "from" to instead use symbol "to" */ def substIdentSyms(from: Symbol, to: Symbol) = { val subs = new TreeSymSubstituter(List(from), List(to)) - AnnotationInfo(atp, args.map(subs(_)), assocs) + AnnotationInfo(atp, args.map(subs(_)), assocs, pos) } } diff --git a/src/compiler/scala/tools/nsc/symtab/Symbols.scala b/src/compiler/scala/tools/nsc/symtab/Symbols.scala index 0d3be5bd2e..128b4ac2a8 100644 --- a/src/compiler/scala/tools/nsc/symtab/Symbols.scala +++ b/src/compiler/scala/tools/nsc/symtab/Symbols.scala @@ -116,7 +116,7 @@ trait Symbols { // see "def typeSig" in Namers val annots1 = initialize.rawannots map { case LazyAnnotationInfo(annot) => annot() - case a @ AnnotationInfo(_, _, _) => a + case a @ AnnotationInfo(_, _, _, _) => a } filter { a => !a.atp.isError } rawannots = annots1 annots1 diff --git a/src/compiler/scala/tools/nsc/symtab/Types.scala b/src/compiler/scala/tools/nsc/symtab/Types.scala index d5e8f0d02c..2a1b8143f4 100644 --- a/src/compiler/scala/tools/nsc/symtab/Types.scala +++ b/src/compiler/scala/tools/nsc/symtab/Types.scala @@ -2163,7 +2163,7 @@ A type's typeSymbol should never be inspected directly. // ** Replace formal type parameter symbols with actual type arguments. * / override def instantiateTypeParams(formals: List[Symbol], actuals: List[Type]) = { val annotations1 = annotations.map(info => AnnotationInfo(info.atp.instantiateTypeParams( - formals, actuals), info.args, info.assocs)) + formals, actuals), info.args, info.assocs, info.pos)) val underlying1 = underlying.instantiateTypeParams(formals, actuals) if ((annotations1 eq annotations) && (underlying1 eq underlying)) this else AnnotatedType(annotations1, underlying1, selfsym) @@ -2785,7 +2785,7 @@ A type's typeSymbol should never be inspected directly. } def mapOver(annot: AnnotationInfo): Option[AnnotationInfo] = { - val AnnotationInfo(atp, args, assocs) = annot + val AnnotationInfo(atp, args, assocs, pos) = annot if (dropNonConstraintAnnotations && !(atp.typeSymbol isNonBottomSubClass TypeConstraintClass)) @@ -2798,7 +2798,7 @@ A type's typeSymbol should never be inspected directly. if ((args eq args1) && (atp eq atp1)) Some(annot) else if (args1.length == args.length) - Some(AnnotationInfo(atp1, args1, assocs)) + Some(AnnotationInfo(atp1, args1, assocs, pos)) else None } diff --git a/src/compiler/scala/tools/nsc/symtab/classfile/ClassfileParser.scala b/src/compiler/scala/tools/nsc/symtab/classfile/ClassfileParser.scala index 6178cf60a3..12e53934ed 100644 --- a/src/compiler/scala/tools/nsc/symtab/classfile/ClassfileParser.scala +++ b/src/compiler/scala/tools/nsc/symtab/classfile/ClassfileParser.scala @@ -793,7 +793,7 @@ abstract class ClassfileParser { } // Attribute on methods of java annotation classes when that method has a default case nme.AnnotationDefaultATTR => - sym.addAnnotation(AnnotationInfo(definitions.AnnotationDefaultAttr.tpe, List(), List())) + sym.addAnnotation(AnnotationInfo(definitions.AnnotationDefaultAttr.tpe, List(), List(), NoPosition)) in.skip(attrLen) // Java annotatinos on classes / methods / fields with RetentionPolicy.RUNTIME case nme.RuntimeAnnotationATTR => @@ -863,7 +863,7 @@ abstract class ClassfileParser { } } if (hasError) None - else Some(AnnotationInfo(attrType, List(), nvpairs.toList)) + else Some(AnnotationInfo(attrType, List(), nvpairs.toList, NoPosition)) } catch { case f: FatalError => throw f // don't eat fatal errors, they mean a class was not found case ex: Throwable => diff --git a/src/compiler/scala/tools/nsc/symtab/classfile/Pickler.scala b/src/compiler/scala/tools/nsc/symtab/classfile/Pickler.scala index 583b05f039..0d339ca5c2 100644 --- a/src/compiler/scala/tools/nsc/symtab/classfile/Pickler.scala +++ b/src/compiler/scala/tools/nsc/symtab/classfile/Pickler.scala @@ -468,7 +468,7 @@ abstract class Pickler extends SubComponent { putAnnotation(annInfo) } } - val AnnotationInfo(tpe, args, assocs) = annot + val AnnotationInfo(tpe, args, assocs, _) = annot putType(tpe) args foreach putAnnotArg assocs foreach { asc => @@ -614,7 +614,7 @@ abstract class Pickler extends SubComponent { } // annotations attached to a symbol (i.e. annots on terms) - case (target: Symbol, annot@AnnotationInfo(_, _, _)) => + case (target: Symbol, annot@AnnotationInfo(_, _, _, _)) => writeRef(target) writeAnnotation(annot) SYMANNOT @@ -966,7 +966,7 @@ abstract class Pickler extends SubComponent { MODIFIERS // annotations on types (not linked to a symbol) - case annot@AnnotationInfo(_, _, _) => + case annot@AnnotationInfo(_, _, _, _) => writeAnnotation(annot) ANNOTINFO @@ -1072,7 +1072,7 @@ abstract class Pickler extends SubComponent { printRef(tp) printRefs(annots) } - case (target: Symbol, AnnotationInfo(atp, args, Nil)) => + case (target: Symbol, AnnotationInfo(atp, args, Nil, _)) => print("SYMANNOT ") printRef(target) printRef(atp) @@ -1081,7 +1081,7 @@ abstract class Pickler extends SubComponent { print("CHILDREN ") printRef(target) for (c <- children) printRef(c.asInstanceOf[Symbol]) - case AnnotationInfo(atp, args, Nil) => + case AnnotationInfo(atp, args, Nil, _) => print("ANNOTINFO") printRef(atp) for (c <- args) printRef(c) diff --git a/src/compiler/scala/tools/nsc/symtab/classfile/UnPickler.scala b/src/compiler/scala/tools/nsc/symtab/classfile/UnPickler.scala index 76c181b783..f3d1c8864b 100644 --- a/src/compiler/scala/tools/nsc/symtab/classfile/UnPickler.scala +++ b/src/compiler/scala/tools/nsc/symtab/classfile/UnPickler.scala @@ -423,7 +423,7 @@ abstract class UnPickler { else args += at(argref, readAnnotArg) } - AnnotationInfo(atp, args.toList, assocs.toList) + AnnotationInfo(atp, args.toList, assocs.toList, NoPosition) } diff --git a/src/compiler/scala/tools/nsc/transform/CleanUp.scala b/src/compiler/scala/tools/nsc/transform/CleanUp.scala index 8136893fcb..2bbe419dab 100644 --- a/src/compiler/scala/tools/nsc/transform/CleanUp.scala +++ b/src/compiler/scala/tools/nsc/transform/CleanUp.scala @@ -9,7 +9,7 @@ package transform import symtab._ import Flags._ -import scala.tools.nsc.util.Position +import scala.tools.nsc.util.{ Position, NoPosition } import scala.collection.mutable.{ListBuffer, HashMap} abstract class CleanUp extends Transform with ast.TreeDSL { @@ -32,10 +32,10 @@ abstract class CleanUp extends Transform with ast.TreeDSL { private var localTyper: analyzer.Typer = null private lazy val serializableAnnotation = - AnnotationInfo(SerializableAttr.tpe, Nil, Nil) + AnnotationInfo(SerializableAttr.tpe, Nil, Nil, NoPosition) private lazy val serialVersionUIDAnnotation = { val attr = definitions.getClass("scala.SerialVersionUID") - AnnotationInfo(attr.tpe, List(Literal(Constant(0))), List()) + AnnotationInfo(attr.tpe, List(Literal(Constant(0))), List(), NoPosition) } private object MethodDispatchType extends scala.Enumeration { diff --git a/src/compiler/scala/tools/nsc/transform/Mixin.scala b/src/compiler/scala/tools/nsc/transform/Mixin.scala index d3c3a86f4c..b14d777e58 100644 --- a/src/compiler/scala/tools/nsc/transform/Mixin.scala +++ b/src/compiler/scala/tools/nsc/transform/Mixin.scala @@ -611,7 +611,7 @@ abstract class Mixin extends InfoTransform with ast.TreeDSL { .setInfo(IntClass.tpe) .setFlag(PROTECTED) atPhase(currentRun.typerPhase) { - sym addAnnotation AnnotationInfo(VolatileAttr.tpe, Nil, Nil) + sym addAnnotation AnnotationInfo(VolatileAttr.tpe, Nil, Nil, NoPosition) } clazz.info.decls.enter(sym) addDef(clazz.pos, VAL(sym) === ZERO) diff --git a/src/compiler/scala/tools/nsc/transform/SpecializeTypes.scala b/src/compiler/scala/tools/nsc/transform/SpecializeTypes.scala index d0e92aebd9..da0abfd403 100644 --- a/src/compiler/scala/tools/nsc/transform/SpecializeTypes.scala +++ b/src/compiler/scala/tools/nsc/transform/SpecializeTypes.scala @@ -271,7 +271,7 @@ abstract class SpecializeTypes extends InfoTransform with TypingTransformers { */ def concreteTypes(sym: Symbol): List[Type] = sym.getAnnotation(SpecializedClass) match { - case Some(AnnotationInfo(_, args, _)) => + case Some(AnnotationInfo(_, args, _, _)) => args match { case Literal(ct) :: _ => val tpes = parseTypes(ct.stringValue) diff --git a/src/compiler/scala/tools/nsc/typechecker/Namers.scala b/src/compiler/scala/tools/nsc/typechecker/Namers.scala index 273d0e42a8..4628c73fdc 100644 --- a/src/compiler/scala/tools/nsc/typechecker/Namers.scala +++ b/src/compiler/scala/tools/nsc/typechecker/Namers.scala @@ -8,7 +8,7 @@ package scala.tools.nsc package typechecker import scala.collection.mutable.HashMap -import scala.tools.nsc.util.Position +import scala.tools.nsc.util.{ Position, NoPosition } import symtab.Flags import symtab.Flags._ @@ -919,7 +919,7 @@ trait Namers { self: Analyzer => } else typer.typedType(tpt).tpe // #2382: return type of default getters are always @uncheckedVariance if (meth.hasFlag(DEFAULTPARAM)) - rt.withAnnotation(AnnotationInfo(definitions.uncheckedVarianceClass.tpe, List(), List())) + rt.withAnnotation(AnnotationInfo(definitions.uncheckedVarianceClass.tpe, List(), List(), NoPosition)) else rt }) } diff --git a/src/compiler/scala/tools/nsc/typechecker/SyntheticMethods.scala b/src/compiler/scala/tools/nsc/typechecker/SyntheticMethods.scala index e3d75752f2..9682726c81 100644 --- a/src/compiler/scala/tools/nsc/typechecker/SyntheticMethods.scala +++ b/src/compiler/scala/tools/nsc/typechecker/SyntheticMethods.scala @@ -9,6 +9,7 @@ package typechecker import symtab.Flags import symtab.Flags._ +import util.NoPosition import scala.collection.mutable.ListBuffer /**