summaryrefslogtreecommitdiff
path: root/src/reflect
diff options
context:
space:
mode:
authorAdriaan Moors <adriaan.moors@typesafe.com>2012-11-16 14:56:55 -0800
committerAdriaan Moors <adriaan.moors@typesafe.com>2012-11-16 14:56:55 -0800
commit6645fec23ab3ee7d12f5cfc7c474a42f0eb7ec15 (patch)
treea4f4cd998a558990315530e67fb06068b836d8ad /src/reflect
parentb091cbda7e3a22f0d4554159b27b1bb30cf4a3a9 (diff)
parented44df6c85e82bc6d4731ed232de53bdbeadb2e1 (diff)
downloadscala-6645fec23ab3ee7d12f5cfc7c474a42f0eb7ec15.tar.gz
scala-6645fec23ab3ee7d12f5cfc7c474a42f0eb7ec15.tar.bz2
scala-6645fec23ab3ee7d12f5cfc7c474a42f0eb7ec15.zip
Merge pull request #1623 from paulp/merge-2.10.x
Merge 2.10.0-wip/.x into master
Diffstat (limited to 'src/reflect')
-rw-r--r--src/reflect/scala/reflect/internal/Definitions.scala1
-rw-r--r--src/reflect/scala/reflect/internal/SymbolTable.scala6
-rw-r--r--src/reflect/scala/reflect/internal/Symbols.scala5
-rw-r--r--src/reflect/scala/reflect/internal/TreeInfo.scala80
-rw-r--r--src/reflect/scala/reflect/internal/Types.scala1
-rw-r--r--src/reflect/scala/reflect/macros/compileTimeOnly.scala16
6 files changed, 91 insertions, 18 deletions
diff --git a/src/reflect/scala/reflect/internal/Definitions.scala b/src/reflect/scala/reflect/internal/Definitions.scala
index ed45010091..8e406b6f62 100644
--- a/src/reflect/scala/reflect/internal/Definitions.scala
+++ b/src/reflect/scala/reflect/internal/Definitions.scala
@@ -981,6 +981,7 @@ trait Definitions extends api.StandardDefinitions {
lazy val BeanPropertyAttr = requiredClass[scala.beans.BeanProperty]
lazy val BooleanBeanPropertyAttr = requiredClass[scala.beans.BooleanBeanProperty]
lazy val CloneableAttr = requiredClass[scala.annotation.cloneable]
+ lazy val CompileTimeOnlyAttr = getClassIfDefined("scala.reflect.macros.compileTimeOnly")
lazy val DeprecatedAttr = requiredClass[scala.deprecated]
lazy val DeprecatedNameAttr = requiredClass[scala.deprecatedName]
lazy val DeprecatedInheritanceAttr = requiredClass[scala.deprecatedInheritance]
diff --git a/src/reflect/scala/reflect/internal/SymbolTable.scala b/src/reflect/scala/reflect/internal/SymbolTable.scala
index 68b5794b59..fb1bf9ed9d 100644
--- a/src/reflect/scala/reflect/internal/SymbolTable.scala
+++ b/src/reflect/scala/reflect/internal/SymbolTable.scala
@@ -6,6 +6,7 @@
package scala.reflect
package internal
+import scala.annotation.elidable
import scala.collection.{ mutable, immutable }
import util._
@@ -108,6 +109,11 @@ abstract class SymbolTable extends macros.Universe
val global: SymbolTable.this.type = SymbolTable.this
} with util.TraceSymbolActivity
+ /** Check that the executing thread is the compiler thread. No-op here,
+ * overridden in interactive.Global. */
+ @elidable(elidable.WARNING)
+ def assertCorrectThread() {}
+
/** Are we compiling for Java SE? */
// def forJVM: Boolean
diff --git a/src/reflect/scala/reflect/internal/Symbols.scala b/src/reflect/scala/reflect/internal/Symbols.scala
index 30e5ecd643..0ad0275fba 100644
--- a/src/reflect/scala/reflect/internal/Symbols.scala
+++ b/src/reflect/scala/reflect/internal/Symbols.scala
@@ -740,6 +740,9 @@ trait Symbols extends api.Symbols { self: SymbolTable =>
def elisionLevel = getAnnotation(ElidableMethodClass) flatMap { _.intArg(0) }
def implicitNotFoundMsg = getAnnotation(ImplicitNotFoundClass) flatMap { _.stringArg(0) }
+ def isCompileTimeOnly = hasAnnotation(CompileTimeOnlyAttr)
+ def compileTimeOnlyMessage = getAnnotation(CompileTimeOnlyAttr) flatMap (_ stringArg 0)
+
/** Is this symbol an accessor method for outer? */
final def isOuterAccessor = {
hasFlag(STABLE | ARTIFACT) &&
@@ -1259,6 +1262,7 @@ trait Symbols extends api.Symbols { self: SymbolTable =>
}
val current = phase
try {
+ assertCorrectThread()
phase = phaseOf(infos.validFrom)
tp.complete(this)
} finally {
@@ -1329,6 +1333,7 @@ trait Symbols extends api.Symbols { self: SymbolTable =>
infos = infos.prev
if (validTo < curPeriod) {
+ assertCorrectThread()
// adapt any infos that come from previous runs
val current = phase
try {
diff --git a/src/reflect/scala/reflect/internal/TreeInfo.scala b/src/reflect/scala/reflect/internal/TreeInfo.scala
index ddfc1f2af0..7ae7cf1821 100644
--- a/src/reflect/scala/reflect/internal/TreeInfo.scala
+++ b/src/reflect/scala/reflect/internal/TreeInfo.scala
@@ -287,6 +287,68 @@ abstract class TreeInfo {
isSelfConstrCall(tree1) || isSuperConstrCall(tree1)
}
+ /**
+ * Does this tree represent an irrefutable pattern match
+ * in the position `for { <tree> <- expr }` based only
+ * on information at the `parser` phase? To qualify, there
+ * may be no subtree that will be interpreted as a
+ * Stable Identifier Pattern.
+ *
+ * For instance:
+ *
+ * {{{
+ * foo @ (bar, (baz, quux))
+ * }}}
+ *
+ * is a variable pattern; if the structure matches,
+ * then the remainder is inevitable.
+ *
+ * The following are not variable patterns.
+ *
+ * {{{
+ * foo @ (bar, (`baz`, quux)) // back quoted ident, not at top level
+ * foo @ (bar, Quux) // UpperCase ident, not at top level
+ * }}}
+ *
+ * If the pattern is a simple identifier, it is always
+ * a variable pattern. For example, the following
+ * introduce new bindings:
+ *
+ * {{{
+ * for { X <- xs } yield X
+ * for { `backquoted` <- xs } yield `backquoted`
+ * }}}
+ *
+ * Note that this differs from a case clause:
+ *
+ * {{{
+ * object X
+ * scrut match {
+ * case X => // case _ if scrut == X
+ * }
+ * }}}
+ *
+ * Background: [[https://groups.google.com/d/msg/scala-internals/qwa_XOw_7Ks/IktkeTBYqg0J]]
+ *
+ */
+ def isVarPatternDeep(tree: Tree): Boolean = {
+ def isVarPatternDeep0(tree: Tree): Boolean = {
+ tree match {
+ case Bind(name, pat) => isVarPatternDeep0(pat)
+ case Ident(name) => isVarPattern(tree)
+ case Apply(sel, args) =>
+ ( isReferenceToScalaMember(sel, TupleClass(args.size).name.toTermName)
+ && (args forall isVarPatternDeep0)
+ )
+ case _ => false
+ }
+ }
+ tree match {
+ case Ident(name) => true
+ case _ => isVarPatternDeep0(tree)
+ }
+ }
+
/** Is tree a variable pattern? */
def isVarPattern(pat: Tree): Boolean = pat match {
case x: Ident => !x.isBackquoted && nme.isVariableName(x.name)
@@ -372,24 +434,6 @@ abstract class TreeInfo {
case _ => false
}
- /** Is this tree comprised of nothing but identifiers,
- * but possibly in bindings or tuples? For instance
- *
- * foo @ (bar, (baz, quux))
- *
- * is a variable pattern; if the structure matches,
- * then the remainder is inevitable.
- */
- def isVariablePattern(tree: Tree): Boolean = tree match {
- case Bind(name, pat) => isVariablePattern(pat)
- case Ident(name) => true
- case Apply(sel, args) =>
- ( isReferenceToScalaMember(sel, TupleClass(args.size).name.toTermName)
- && (args forall isVariablePattern)
- )
- case _ => false
- }
-
/** Is this argument node of the form <expr> : _* ?
*/
def isWildcardStarArg(tree: Tree): Boolean = tree match {
diff --git a/src/reflect/scala/reflect/internal/Types.scala b/src/reflect/scala/reflect/internal/Types.scala
index 02cdac4046..42a9d9e456 100644
--- a/src/reflect/scala/reflect/internal/Types.scala
+++ b/src/reflect/scala/reflect/internal/Types.scala
@@ -143,6 +143,7 @@ trait Types extends api.Types { self: SymbolTable =>
/** Undo all changes to constraints to type variables upto `limit`. */
//OPT this method is public so we can do `manual inlining`
def undoTo(limit: UndoPairs) {
+ assertCorrectThread()
while ((log ne limit) && log.nonEmpty) {
val (tv, constr) = log.head
tv.constr = constr
diff --git a/src/reflect/scala/reflect/macros/compileTimeOnly.scala b/src/reflect/scala/reflect/macros/compileTimeOnly.scala
new file mode 100644
index 0000000000..5a3a352a53
--- /dev/null
+++ b/src/reflect/scala/reflect/macros/compileTimeOnly.scala
@@ -0,0 +1,16 @@
+package scala.reflect
+package macros
+
+import scala.annotation.meta._
+
+/**
+ * An annotation that designates a member should not be referred to after
+ * type checking (which includes macro expansion); it must only be used in
+ * the arguments of some other macro that will eliminate it from the AST.
+ *
+ * @param message the error message to print during compilation if a reference remains
+ * after type checking
+ * @since 2.10.1
+ */
+@getter @setter @beanGetter @beanSetter
+final class compileTimeOnly(message: String) extends scala.annotation.StaticAnnotation