aboutsummaryrefslogtreecommitdiff
path: root/src/dotty
diff options
context:
space:
mode:
authorMartin Odersky <odersky@gmail.com>2014-02-11 14:42:45 +0100
committerMartin Odersky <odersky@gmail.com>2014-02-11 14:42:56 +0100
commit459d78dccc40c94dd7da8b5b29762a494595778b (patch)
tree2d678de090302dab70d7079730f8ed4cc258b667 /src/dotty
parente895249de8f59e5a5c4175b428193fa4c5ea90af (diff)
downloaddotty-459d78dccc40c94dd7da8b5b29762a494595778b.tar.gz
dotty-459d78dccc40c94dd7da8b5b29762a494595778b.tar.bz2
dotty-459d78dccc40c94dd7da8b5b29762a494595778b.zip
New scheme for attachments.
Added general way to put attachments on some base type (which needs to inherit from Attachment.Container). Used it to turn typedTree map into an attachment. Also, moved DotClass to dotc.util.
Diffstat (limited to 'src/dotty')
-rw-r--r--src/dotty/tools/dotc/Driver.scala2
-rw-r--r--src/dotty/tools/dotc/ast/Trees.scala4
-rw-r--r--src/dotty/tools/dotc/config/CompilerCommand.scala2
-rw-r--r--src/dotty/tools/dotc/core/Denotations.scala2
-rw-r--r--src/dotty/tools/dotc/core/Names.scala1
-rw-r--r--src/dotty/tools/dotc/core/Periods.scala1
-rw-r--r--src/dotty/tools/dotc/core/Phases.scala4
-rw-r--r--src/dotty/tools/dotc/core/Symbols.scala13
-rw-r--r--src/dotty/tools/dotc/core/Transformers.scala7
-rw-r--r--src/dotty/tools/dotc/core/TypeComparer.scala3
-rw-r--r--src/dotty/tools/dotc/core/TyperState.scala2
-rw-r--r--src/dotty/tools/dotc/core/Types.scala2
-rw-r--r--src/dotty/tools/dotc/parsing/Parsers.scala4
-rw-r--r--src/dotty/tools/dotc/typer/Namer.scala25
-rw-r--r--src/dotty/tools/dotc/typer/Typer.scala2
-rw-r--r--src/dotty/tools/dotc/util/Attachment.scala65
-rw-r--r--src/dotty/tools/dotc/util/DotClass.scala (renamed from src/dotty/tools/dotc/core/DotClass.scala)2
17 files changed, 114 insertions, 27 deletions
diff --git a/src/dotty/tools/dotc/Driver.scala b/src/dotty/tools/dotc/Driver.scala
index fd2b776f8..892e4cf7d 100644
--- a/src/dotty/tools/dotc/Driver.scala
+++ b/src/dotty/tools/dotc/Driver.scala
@@ -2,7 +2,7 @@ package dotty.tools.dotc
import config.CompilerCommand
import core.Contexts.{Context, ContextBase}
-import core.DotClass
+import util.DotClass
import reporting._
abstract class Driver extends DotClass {
diff --git a/src/dotty/tools/dotc/ast/Trees.scala b/src/dotty/tools/dotc/ast/Trees.scala
index 13f7d6f18..96a91654d 100644
--- a/src/dotty/tools/dotc/ast/Trees.scala
+++ b/src/dotty/tools/dotc/ast/Trees.scala
@@ -11,7 +11,7 @@ import collection.immutable.IndexedSeq
import collection.mutable.ListBuffer
import parsing.Tokens.Token
import printing.Printer
-import util.Stats
+import util.{Stats, Attachment, DotClass}
import annotation.unchecked.uncheckedVariance
object Trees {
@@ -29,7 +29,7 @@ object Trees {
/** A base class for things that have positions (currently: modifiers and trees)
*/
- abstract class Positioned extends DotClass with Product {
+ abstract class Positioned extends Attachment.Container with Product {
private[this] var curPos: Position = _
diff --git a/src/dotty/tools/dotc/config/CompilerCommand.scala b/src/dotty/tools/dotc/config/CompilerCommand.scala
index f4c6ea014..ec8b17b0d 100644
--- a/src/dotty/tools/dotc/config/CompilerCommand.scala
+++ b/src/dotty/tools/dotc/config/CompilerCommand.scala
@@ -5,7 +5,7 @@ package config
import java.io.File
import Settings._
import core.Contexts._
-import core.DotClass
+import util.DotClass
import Properties._
object CompilerCommand extends DotClass {
diff --git a/src/dotty/tools/dotc/core/Denotations.scala b/src/dotty/tools/dotc/core/Denotations.scala
index 19d80db18..5ca53b04e 100644
--- a/src/dotty/tools/dotc/core/Denotations.scala
+++ b/src/dotty/tools/dotc/core/Denotations.scala
@@ -90,7 +90,7 @@ object Denotations {
*
* Then the denotation of `y` is `SingleDenotation(NoSymbol, A | B)`.
*/
- abstract class Denotation extends DotClass with printing.Showable {
+ abstract class Denotation extends util.DotClass with printing.Showable {
/** The referencing symbol, exists only for non-overloaded denotations */
def symbol: Symbol
diff --git a/src/dotty/tools/dotc/core/Names.scala b/src/dotty/tools/dotc/core/Names.scala
index 30f82e05e..09fa6cf19 100644
--- a/src/dotty/tools/dotc/core/Names.scala
+++ b/src/dotty/tools/dotc/core/Names.scala
@@ -12,6 +12,7 @@ import collection.generic.CanBuildFrom
import collection.mutable.{ Builder, StringBuilder }
import collection.immutable.WrappedString
import collection.generic.CanBuildFrom
+import util.DotClass
//import annotation.volatile
object Names {
diff --git a/src/dotty/tools/dotc/core/Periods.scala b/src/dotty/tools/dotc/core/Periods.scala
index 2a38acd15..04eef6aaf 100644
--- a/src/dotty/tools/dotc/core/Periods.scala
+++ b/src/dotty/tools/dotc/core/Periods.scala
@@ -1,6 +1,7 @@
package dotty.tools.dotc.core
import Contexts._
+import dotty.tools.dotc.util.DotClass
/** Periods are the central "clock" of the compiler.
* A period consists of a run id and a phase id.
diff --git a/src/dotty/tools/dotc/core/Phases.scala b/src/dotty/tools/dotc/core/Phases.scala
index 72ebc7129..14cab9821 100644
--- a/src/dotty/tools/dotc/core/Phases.scala
+++ b/src/dotty/tools/dotc/core/Phases.scala
@@ -1,7 +1,9 @@
package dotty.tools.dotc
package core
-import Periods._, Contexts._
+import Periods._
+import Contexts._
+import util.DotClass
trait Phases { self: Context =>
import Phases._
diff --git a/src/dotty/tools/dotc/core/Symbols.scala b/src/dotty/tools/dotc/core/Symbols.scala
index a574c5ec2..4aa1ef94d 100644
--- a/src/dotty/tools/dotc/core/Symbols.scala
+++ b/src/dotty/tools/dotc/core/Symbols.scala
@@ -4,20 +4,27 @@ package core
import Periods._
import Transformers._
-import Names._, Scopes._
+import Names._
+import Scopes._
import Flags._
import java.lang.AssertionError
import Decorators._
import Symbols._
import Contexts._
-import SymDenotations._, printing.Texts._
+import SymDenotations._
+import printing.Texts._
import printing.Printer
-import Types._, Annotations._, util.Positions._, StdNames._, NameOps._
+import Types._
+import Annotations._
+import util.Positions._
+import StdNames._
+import NameOps._
import ast.tpd.{TreeMapper, SharedTree}
import Denotations.{ Denotation, SingleDenotation, MultiDenotation }
import collection.mutable
import io.AbstractFile
import language.implicitConversions
+import util.DotClass
/** Creation methods for symbols */
trait Symbols { this: Context =>
diff --git a/src/dotty/tools/dotc/core/Transformers.scala b/src/dotty/tools/dotc/core/Transformers.scala
index ba26c8be8..90df3a274 100644
--- a/src/dotty/tools/dotc/core/Transformers.scala
+++ b/src/dotty/tools/dotc/core/Transformers.scala
@@ -1,8 +1,13 @@
package dotty.tools.dotc
package core
-import Periods._, SymDenotations._, Contexts._, Types._, Denotations._
+import Periods._
+import SymDenotations._
+import Contexts._
+import Types._
+import Denotations._
import java.lang.AssertionError
+import dotty.tools.dotc.util.DotClass
trait Transformers
diff --git a/src/dotty/tools/dotc/core/TypeComparer.scala b/src/dotty/tools/dotc/core/TypeComparer.scala
index 72d8472b6..1d2d4bac9 100644
--- a/src/dotty/tools/dotc/core/TypeComparer.scala
+++ b/src/dotty/tools/dotc/core/TypeComparer.scala
@@ -8,8 +8,7 @@ import Decorators._
import StdNames.{nme, tpnme}
import collection.mutable
import printing.Disambiguation.disambiguated
-import util.SimpleMap
-import util.Stats
+import util.{SimpleMap, Stats, DotClass}
import config.Config
import config.Printers._
diff --git a/src/dotty/tools/dotc/core/TyperState.scala b/src/dotty/tools/dotc/core/TyperState.scala
index 13fbdbe15..e0c7481c8 100644
--- a/src/dotty/tools/dotc/core/TyperState.scala
+++ b/src/dotty/tools/dotc/core/TyperState.scala
@@ -5,7 +5,7 @@ package core
import Types._
import Flags._
import Contexts._
-import util.SimpleMap
+import util.{SimpleMap, DotClass}
import reporting._
import printing.{Showable, Printer}
import printing.Texts._
diff --git a/src/dotty/tools/dotc/core/Types.scala b/src/dotty/tools/dotc/core/Types.scala
index 49b57d32f..377b20991 100644
--- a/src/dotty/tools/dotc/core/Types.scala
+++ b/src/dotty/tools/dotc/core/Types.scala
@@ -16,7 +16,7 @@ import Denotations._
import Periods._
import util.Positions.Position
import util.Stats._
-import util.SimpleMap
+import util.{DotClass, SimpleMap}
import ast.tpd._, printing.Texts._
import ast.untpd
import transform.Erasure
diff --git a/src/dotty/tools/dotc/parsing/Parsers.scala b/src/dotty/tools/dotc/parsing/Parsers.scala
index cf0ab9f62..ceb4ebe42 100644
--- a/src/dotty/tools/dotc/parsing/Parsers.scala
+++ b/src/dotty/tools/dotc/parsing/Parsers.scala
@@ -12,7 +12,8 @@ import core._
import Flags._
import Contexts._
import Names._
-import ast.Trees._, ast.TreeInfo
+import ast.Trees._
+import ast.TreeInfo
import Decorators._
import StdNames._
import util.Positions._
@@ -22,6 +23,7 @@ import NameOps._
import util.Chars._
import ScriptParsers._
import annotation.switch
+import util.DotClass
object Parsers {
diff --git a/src/dotty/tools/dotc/typer/Namer.scala b/src/dotty/tools/dotc/typer/Namer.scala
index 776d59542..da90a0ab3 100644
--- a/src/dotty/tools/dotc/typer/Namer.scala
+++ b/src/dotty/tools/dotc/typer/Namer.scala
@@ -9,7 +9,7 @@ import Contexts._, Symbols._, Types._, SymDenotations._, Names._, NameOps._, Fla
import ast.desugar, ast.desugar._
import Inferencing._
import util.Positions._
-import util.SourcePosition
+import util.{Attachment, SourcePosition, DotClass}
import collection.mutable
import annotation.tailrec
import ErrorReporting._
@@ -96,10 +96,15 @@ class Namer { typer: Typer =>
import untpd._
+ val TypedAhead = new Attachment.Key[tpd.Tree]
+ val ExpandedTree = new Attachment.Key[Tree]
+ val SymOfTree = new Attachment.Key[Symbol]
+
/** A partial map from unexpanded member and pattern defs and to their expansions.
* Populated during enterSyms, emptied during typer.
*/
- lazy val expandedTree = new mutable.AnyRefMap[DefTree, Tree] /*{
+ lazy val expandedTree = new mutable.AnyRefMap[DefTree, Tree]
+ /*{
override def default(tree: DefTree) = tree // can't have defaults on AnyRefMaps :-(
}*/
@@ -113,7 +118,7 @@ class Namer { typer: Typer =>
/** A map from expanded trees to their typed versions.
* Populated when trees are typechecked during completion (using method typedAhead).
*/
- lazy val typedTree = new mutable.AnyRefMap[Tree, tpd.Tree]
+ // lazy val typedTree = new mutable.AnyRefMap[Tree, tpd.Tree]
/** A map from method symbols to nested typers.
* Populated when methods are completed. Emptied when they are typechecked.
@@ -133,9 +138,9 @@ class Namer { typer: Typer =>
/** The symbol of the given expanded tree. */
def symbolOfTree(tree: Tree)(implicit ctx: Context): Symbol = {
val xtree = expanded(tree)
- typedTree get xtree match {
- case Some(ttree) => ttree.denot.symbol
- case _ => symOfTree(xtree)
+ xtree.getAttachment(TypedAhead) match {
+ case Some(ttree) => ttree.symbol
+ case none => symOfTree(xtree)
}
}
@@ -249,12 +254,14 @@ class Namer { typer: Typer =>
val expanded = desugar.defTree(mdef)
typr.println(i"Expansion: $mdef expands to $expanded")
if (expanded ne mdef) expandedTree(mdef) = expanded
+ // if (expanded ne mdef) mdef.pushAttachment(ExpandedTree(expanded))
case _ =>
}
/** The expanded version of this tree, or tree itself if not expanded */
def expanded(tree: Tree)(implicit ctx: Context): Tree = tree match {
case ddef: DefTree => expandedTree.getOrElse(ddef, ddef)
+ //ddef.getAttachment(ExpandedTreeKey).orElse(ddef).asInstanceOf[Tree]
case _ => tree
}
@@ -445,15 +452,13 @@ class Namer { typer: Typer =>
/** Typecheck tree during completion, and remember result in typedtree map */
private def typedAheadImpl(tree: Tree, pt: Type)(implicit ctx: Context): tpd.Tree = {
val xtree = expanded(tree)
- typedTree.get(xtree) match {
+ xtree.getAttachment(TypedAhead) match {
case Some(ttree) => ttree
case none =>
val ttree = typer.typed(tree, pt)
- typedTree(xtree) = ttree
+ xtree.pushAttachment(TypedAhead, ttree)
ttree
}
- // was: typedTree.getOrElseUpdate(expanded(tree), typer.typed(tree, pt))
- // but this fails for AnyRefMap with an ArrayIndexOutOfBounds exception in getOrElseUpdate
}
def typedAheadType(tree: Tree, pt: Type = WildcardType)(implicit ctx: Context): tpd.Tree =
diff --git a/src/dotty/tools/dotc/typer/Typer.scala b/src/dotty/tools/dotc/typer/Typer.scala
index 697441ca1..e68109c9b 100644
--- a/src/dotty/tools/dotc/typer/Typer.scala
+++ b/src/dotty/tools/dotc/typer/Typer.scala
@@ -964,7 +964,7 @@ class Typer extends Namer with Applications with Implicits {
def typedUnadapted(initTree: untpd.Tree, pt: Type = WildcardType)(implicit ctx: Context): Tree = {
val xtree = expanded(initTree)
- typedTree remove xtree match {
+ xtree.removeAttachment(TypedAhead) match {
case Some(ttree) => ttree
case none =>
val sym = symOfTree.getOrElse(xtree, NoSymbol)
diff --git a/src/dotty/tools/dotc/util/Attachment.scala b/src/dotty/tools/dotc/util/Attachment.scala
new file mode 100644
index 000000000..dc9602df3
--- /dev/null
+++ b/src/dotty/tools/dotc/util/Attachment.scala
@@ -0,0 +1,65 @@
+package dotty.tools.dotc.util
+
+/** A class inheriting from Attachment.Container supports
+ * adding, removing and lookup of attachments. Attachments are typed key/value pairs.
+ */
+object Attachment {
+
+ class Key[+V]
+
+ val NullKey = new Key[Null]
+
+ abstract class AttachmentLink[+V] extends DotClass {
+ private[Attachment] def key: Key[V]
+ private[Attachment] def value: V
+ private[Attachment] var next: Link[_]
+
+ def getAttachment[V](key: Key[V]): Option[V] =
+ if (this.key eq key) Some(this.value.asInstanceOf[V])
+ else if (next == null) None
+ else next.getAttachment(key)
+
+ def pushAttachment[V](key: Key[V], value: V): Unit = {
+ assert(!getAttachment(key).isDefined)
+ next = new Link(key, value, next)
+ }
+
+ def putAttachment[V](key: Key[V], value: V): Option[V] = {
+ if (next == null) {
+ next = new Link(key, value, null)
+ None
+ }
+ else if (next.key eq key) {
+ val nx = next
+ next = new Link(key, value, nx.next)
+ Some(nx.value.asInstanceOf[V])
+ }
+ else next.putAttachment(key, value)
+ }
+
+ def removeAttachment[V](key: Key[V]): Option[V] = {
+ if (next == null)
+ None
+ else if (next.key eq key) {
+ val nx = next
+ next = nx.next
+ Some(nx.value.asInstanceOf[V])
+ }
+ else next.removeAttachment(key)
+ }
+
+ def allAttachments: List[Any] =
+ if (next == null) Nil else next.allAttachments
+ }
+
+ private[Attachment] class Link[+V](val key: Key[V], val value: V, var next: Link[_])
+ extends AttachmentLink[V] {
+ override def allAttachments: List[Any] = value :: super.allAttachments
+ }
+
+ class Container extends AttachmentLink[Null] {
+ private[Attachment] def key = NullKey
+ private[Attachment] def value: Null = unsupported("value")
+ private[Attachment] var next: Link[_] = null
+ }
+} \ No newline at end of file
diff --git a/src/dotty/tools/dotc/core/DotClass.scala b/src/dotty/tools/dotc/util/DotClass.scala
index f74a4ba81..7839fc37d 100644
--- a/src/dotty/tools/dotc/core/DotClass.scala
+++ b/src/dotty/tools/dotc/util/DotClass.scala
@@ -1,4 +1,4 @@
-package dotty.tools.dotc.core
+package dotty.tools.dotc.util
/** Adds standard functionality to a class.
* For now: Just the `unsupported` method.