summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--src/compiler/scala/reflect/macros/compiler/Errors.scala4
-rw-r--r--src/compiler/scala/reflect/macros/compiler/Resolvers.scala44
-rw-r--r--src/compiler/scala/tools/nsc/Global.scala20
-rw-r--r--src/reflect/scala/reflect/internal/Definitions.scala18
-rw-r--r--src/reflect/scala/reflect/internal/StdNames.scala4
-rw-r--r--src/reflect/scala/reflect/internal/TreeGen.scala3
-rw-r--r--src/repl/scala/tools/nsc/interpreter/MemberHandlers.scala10
-rw-r--r--test/files/neg/macro-bundle-abstract.check4
-rw-r--r--test/files/neg/macro-bundle-abstract.scala12
-rw-r--r--test/files/neg/macro-bundle-class.check4
-rw-r--r--test/files/neg/macro-bundle-class.scala11
-rw-r--r--test/files/neg/macro-bundle-nonmacro.check4
-rw-r--r--test/files/neg/macro-bundle-nonmacro.scala9
-rw-r--r--test/files/neg/macro-bundle-object.check7
-rw-r--r--test/files/neg/macro-bundle-object.scala12
-rw-r--r--test/files/neg/macro-bundle-polymorphic.check10
-rw-r--r--test/files/neg/macro-bundle-polymorphic.scala13
-rw-r--r--test/files/neg/macro-bundle-trait.check4
-rw-r--r--test/files/neg/macro-bundle-trait.scala12
-rw-r--r--test/files/run/macro-bundle-repl.check24
-rw-r--r--test/files/run/macro-bundle-repl.scala13
-rw-r--r--test/files/run/macro-bundle-static.check6
-rw-r--r--test/files/run/macro-bundle-static/Impls_Macros_1.scala31
-rw-r--r--test/files/run/macro-bundle-static/Test_2.scala8
-rw-r--r--test/files/run/macro-bundle-toplevel.check6
-rw-r--r--test/files/run/macro-bundle-toplevel.flags (renamed from test/files/run/macro-bundle.flags)0
-rw-r--r--test/files/run/macro-bundle-toplevel/Impls_Macros_1.scala (renamed from test/files/run/macro-bundle/Impls_Macros_1.scala)13
-rw-r--r--test/files/run/macro-bundle-toplevel/Test_2.scala (renamed from test/files/run/macro-bundle/Test_2.scala)3
-rw-r--r--test/files/run/macro-bundle.check3
29 files changed, 269 insertions, 43 deletions
diff --git a/src/compiler/scala/reflect/macros/compiler/Errors.scala b/src/compiler/scala/reflect/macros/compiler/Errors.scala
index 6ec111cf7c..9b56e417e2 100644
--- a/src/compiler/scala/reflect/macros/compiler/Errors.scala
+++ b/src/compiler/scala/reflect/macros/compiler/Errors.scala
@@ -29,6 +29,10 @@ trait Errors extends Traces {
def MacroImplWrongNumberOfTypeArgumentsError() = implRefError(TypedApplyWrongNumberOfTpeParametersErrorMessage(macroImplRef))
+ def MacroBundleNonStaticError() = implRefError("macro bundles must be static")
+
+ def MacroBundleWrongShapeError() = implRefError("macro bundles must be monomorphic traits extending scala.reflect.macros.Macro and not implementing its `val c: Context` member")
+
// compatibility errors
// helpers
diff --git a/src/compiler/scala/reflect/macros/compiler/Resolvers.scala b/src/compiler/scala/reflect/macros/compiler/Resolvers.scala
index 46c4e24817..49a5c01ad7 100644
--- a/src/compiler/scala/reflect/macros/compiler/Resolvers.scala
+++ b/src/compiler/scala/reflect/macros/compiler/Resolvers.scala
@@ -9,7 +9,7 @@ trait Resolvers {
import global._
import analyzer._
- import definitions._
+ import definitions.{EmptyPackageClass => _, _}
import treeInfo._
import gen._
@@ -33,7 +33,7 @@ trait Resolvers {
*/
lazy val macroImplRef: Tree = {
val (maybeBundleRef, methName, targs) = macroDdef.rhs match {
- case Applied(methRef @ Select(bundleRef @ RefTree(qual, bundleName), methName), targs, Nil) =>
+ case Applied(Select(Applied(RefTree(qual, bundleName), _, Nil), methName), targs, Nil) =>
(RefTree(qual, bundleName.toTypeName), methName, targs)
case Applied(Ident(methName), targs, Nil) =>
(Ident(context.owner.enclClass), methName, targs)
@@ -41,30 +41,36 @@ trait Resolvers {
(EmptyTree, TermName(""), Nil)
}
- val untypedImplRef = typer.silent(_.typedType(maybeBundleRef)) match {
- case SilentResultValue(result) if isMacroBundleType(result.tpe) =>
- val bundleClass = result.tpe.typeSymbol
- if (!bundleClass.owner.isPackageClass) abort(macroDef.pos, "macro bundles can only be defined as top-level classes or traits")
+ val untypedImplRef = typer.silent(_.typedTypeConstructor(maybeBundleRef)) match {
+ case SilentResultValue(result) if result.tpe.baseClasses.contains(MacroClass) =>
+ val bundleProto = result.tpe.typeSymbol
+ val bundlePkg = bundleProto.enclosingPackageClass
+ if (!isMacroBundleProtoType(bundleProto.tpe)) MacroBundleWrongShapeError()
+ if (!bundleProto.owner.isStaticOwner) MacroBundleNonStaticError()
- // synthesize the invoker, i.e. given a top-level `trait Foo extends Macro { def expand = ... } `
- // create a top-level definition `class FooInvoker(val c: Context) extends Foo` in MACRO_INVOKER_PACKAGE
- val invokerPid = gen.mkUnattributedRef(nme.MACRO_INVOKER_PACKAGE)
- val invokerName = TypeName(bundleClass.fullName.split('.').map(_.capitalize).mkString("") + nme.MACRO_INVOKER_SUFFIX)
- val invokerFullName = TypeName(s"$invokerPid.$invokerName")
- val existingInvoker = rootMirror.getClassIfDefined(invokerFullName)
- if (!currentRun.compiles(existingInvoker)) {
+ // synthesize the bundle, i.e. given a static `trait Foo extends Macro { def expand = ... } `
+ // create a top-level definition `class Foo$Bundle(val c: Context) extends Foo` in a package next to `Foo`
+ val bundlePid = gen.mkUnattributedRef(bundlePkg)
+ val bundlePrefix =
+ if (bundlePkg == EmptyPackageClass) bundleProto.fullName('$')
+ else bundleProto.fullName('$').substring(bundlePkg.fullName('$').length + 1)
+ val bundleName = TypeName(bundlePrefix + tpnme.MACRO_BUNDLE_SUFFIX)
+ val existingBundle = bundleProto.enclosingPackageClass.info.decl(bundleName)
+ if (!currentRun.compiles(existingBundle)) {
def mkContextValDef(flags: Long) = ValDef(Modifiers(flags), nme.c, TypeTree(ctxTpe), EmptyTree)
val contextField = mkContextValDef(PARAMACCESSOR)
val contextParam = mkContextValDef(PARAM | PARAMACCESSOR)
- val invokerCtor = DefDef(Modifiers(), nme.CONSTRUCTOR, Nil, List(List(contextParam)), TypeTree(), Block(List(pendingSuperCall), Literal(Constant(()))))
- val invoker = atPos(bundleClass.pos)(ClassDef(NoMods, invokerName, Nil, Template(List(Ident(bundleClass)), noSelfType, List(contextField, invokerCtor))))
- currentRun.compileLate(PackageDef(invokerPid, List(invoker)))
+ val bundleCtor = DefDef(Modifiers(), nme.CONSTRUCTOR, Nil, List(List(contextParam)), TypeTree(), Block(List(pendingSuperCall), Literal(Constant(()))))
+ val bundleParent = gen.mkAppliedTypeTree(Ident(bundleProto), bundleProto.typeParams.map(sym => Ident(sym.name)))
+ val bundleTemplate = Template(List(bundleParent), noSelfType, List(contextField, bundleCtor))
+ val bundle = atPos(bundleProto.pos)(ClassDef(NoMods, bundleName, bundleProto.typeParams.map(TypeDef(_)), bundleTemplate))
+ currentRun.compileLate(bundleName + ".scala", PackageDef(bundlePid, List(bundle)))
}
// synthesize the macro impl reference, which is going to look like:
- // `new Foo$invoker(???).expand` plus the optional type arguments
- val instanceOfInvoker = New(Select(invokerPid, invokerName), List(List(Select(scalaDot(nme.Predef), nme.???))))
- gen.mkTypeApply(Select(instanceOfInvoker, methName), targs)
+ // `new FooBundle(???).macroName` plus the optional type arguments
+ val bundleInstance = New(Select(bundlePid, bundleName), List(List(Ident(Predef_???))))
+ atPos(macroDdef.rhs.pos)(gen.mkTypeApply(Select(bundleInstance, methName), targs))
case _ =>
macroDdef.rhs
}
diff --git a/src/compiler/scala/tools/nsc/Global.scala b/src/compiler/scala/tools/nsc/Global.scala
index ef9d8a310e..92bfe6e0fe 100644
--- a/src/compiler/scala/tools/nsc/Global.scala
+++ b/src/compiler/scala/tools/nsc/Global.scala
@@ -1692,19 +1692,19 @@ class Global(var currentSettings: Settings, var reporter: Reporter)
}
}
- // TODO: provide a way to specify a pretty name for debugging purposes
- private def randomFileName() = (
- "compileLateSynthetic-" + randomUUID().toString.replace("-", "") + ".scala"
- )
-
- def compileLate(code: PackageDef) {
+ /** Create and compile a synthetic compilation unit from the provided tree.
+ *
+ * This needs to create a virtual file underlying the compilation unit in order to appease SBT.
+ * However this file cannot have a randomly generated name, because then SBT 0.13 goes into a vicious loop
+ * as described on the mailing list: https://groups.google.com/forum/#!msg/scala-user/r1SgSoVfs0U/Wv4av0LOKukJ
+ * Therefore I have introduced an additional parameter that makes everyone specify meaningful file names.
+ */
+ def compileLate(virtualFileName: String, code: PackageDef) {
// compatibility with SBT
// on the one hand, we need to specify some jfile here, otherwise sbt crashes with an NPE (SI-6870)
// on the other hand, we can't specify the obvious enclosingUnit, because then sbt somehow fails to run tests using type macros
- // okay, now let's specify a guaranteedly non-existent file in an existing directory (so that we don't run into permission problems)
- val syntheticFileName = randomFileName()
- val fakeJfile = new java.io.File(syntheticFileName)
- val virtualFile = new VirtualFile(syntheticFileName) { override def file = fakeJfile }
+ val fakeJfile = new java.io.File(virtualFileName)
+ val virtualFile = new VirtualFile(virtualFileName) { override def file = fakeJfile }
val sourceFile = new BatchSourceFile(virtualFile, code.toString)
val unit = new CompilationUnit(sourceFile)
unit.body = code
diff --git a/src/reflect/scala/reflect/internal/Definitions.scala b/src/reflect/scala/reflect/internal/Definitions.scala
index 7555df6775..7b2e40b59c 100644
--- a/src/reflect/scala/reflect/internal/Definitions.scala
+++ b/src/reflect/scala/reflect/internal/Definitions.scala
@@ -541,6 +541,7 @@ trait Definitions extends api.StandardDefinitions {
lazy val LiftableClass = getClassIfDefined("scala.reflect.api.Liftable") // defined in scala-reflect.jar, so we need to be careful
lazy val MacroClass = getClassIfDefined("scala.reflect.macros.Macro") // defined in scala-reflect.jar, so we need to be careful
+ def MacroContextValue = MacroClass.map(sym => getMemberValue(sym, nme.c))
lazy val MacroContextClass = getClassIfDefined("scala.reflect.macros.Context") // defined in scala-reflect.jar, so we need to be careful
def MacroContextPrefix = MacroContextClass.map(sym => getMemberMethod(sym, nme.prefix))
def MacroContextPrefixType = MacroContextClass.map(sym => getTypeMember(sym, tpnme.PrefixType))
@@ -640,10 +641,21 @@ trait Definitions extends api.StandardDefinitions {
def unspecializedTypeArgs(tp: Type): List[Type] =
(tp baseType unspecializedSymbol(tp.typeSymbolDirect)).typeArgs
- def isMacroBundleType(tp: Type) = {
+ def isMacroBundleType(tp: Type) = tp.baseClasses match {
+ case _ :: proto :: _ if isMacroBundleProtoType(proto.tpe) => true
+ case _ => false
+ }
+
+ def isMacroBundleProtoType(tp: Type) = {
+ val sym = tp.typeSymbol
val isNonTrivial = tp != ErrorType && tp != NothingTpe && tp != NullTpe
- val isMacroCompatible = MacroClass != NoSymbol && tp <:< MacroClass.tpe
- isNonTrivial && isMacroCompatible
+ val isMacroCompatible = MacroClass != NoSymbol && tp.baseClasses.contains(MacroClass)
+ val isBundlePrototype = sym != MacroClass && sym.isTrait && {
+ val c = sym.info.member(nme.c)
+ val cIsOk = c.overrideChain.contains(MacroContextValue) && c.isDeferred
+ cIsOk && sym.isMonomorphicType
+ }
+ isNonTrivial && isMacroCompatible && isBundlePrototype
}
def isIterableType(tp: Type) = tp <:< classExistentialType(IterableClass)
diff --git a/src/reflect/scala/reflect/internal/StdNames.scala b/src/reflect/scala/reflect/internal/StdNames.scala
index c1fd5b3cd6..0aee71c26e 100644
--- a/src/reflect/scala/reflect/internal/StdNames.scala
+++ b/src/reflect/scala/reflect/internal/StdNames.scala
@@ -214,6 +214,7 @@ trait StdNames {
final val WILDCARD_STAR: NameType = "_*"
final val REIFY_TREECREATOR_PREFIX: NameType = "$treecreator"
final val REIFY_TYPECREATOR_PREFIX: NameType = "$typecreator"
+ final val MACRO_BUNDLE_SUFFIX: NameType = "$Bundle"
final val Any: NameType = "Any"
final val AnyVal: NameType = "AnyVal"
@@ -307,9 +308,6 @@ trait StdNames {
val FAKE_LOCAL_THIS: NameType = "this$"
val LAZY_LOCAL: NameType = "$lzy"
val LAZY_SLOW_SUFFIX: NameType = "$lzycompute"
- val MACRO_INVOKER_PACKAGE: NameType = "scala.reflect.macros.synthetic"
- // TODO: if I use dollars in MACRO_INVOKER_SUFFIX, as in "$Invoker$", then Scala reflection fails to load implementations
- val MACRO_INVOKER_SUFFIX: NameType = "Invoker"
val UNIVERSE_BUILD_PREFIX: NameType = "$u.build."
val UNIVERSE_PREFIX: NameType = "$u."
val UNIVERSE_SHORT: NameType = "$u"
diff --git a/src/reflect/scala/reflect/internal/TreeGen.scala b/src/reflect/scala/reflect/internal/TreeGen.scala
index e44461f964..720d8bfe4a 100644
--- a/src/reflect/scala/reflect/internal/TreeGen.scala
+++ b/src/reflect/scala/reflect/internal/TreeGen.scala
@@ -209,7 +209,8 @@ abstract class TreeGen extends macros.TreeBuilder {
/** Builds a type application node if args.nonEmpty, returns fun otherwise. */
def mkTypeApply(fun: Tree, targs: List[Tree]): Tree =
if (targs.isEmpty) fun else TypeApply(fun, targs)
-
+ def mkAppliedTypeTree(fun: Tree, targs: List[Tree]): Tree =
+ if (targs.isEmpty) fun else AppliedTypeTree(fun, targs)
def mkAttributedTypeApply(target: Tree, method: Symbol, targs: List[Type]): Tree =
mkTypeApply(mkAttributedSelect(target, method), targs map TypeTree)
diff --git a/src/repl/scala/tools/nsc/interpreter/MemberHandlers.scala b/src/repl/scala/tools/nsc/interpreter/MemberHandlers.scala
index 28b95aa442..f4cbcb50fe 100644
--- a/src/repl/scala/tools/nsc/interpreter/MemberHandlers.scala
+++ b/src/repl/scala/tools/nsc/interpreter/MemberHandlers.scala
@@ -87,10 +87,11 @@ trait MemberHandlers {
def definesTerm = Option.empty[TermName]
def definesType = Option.empty[TypeName]
- lazy val referencedNames = ImportVarsTraverser(member)
- def importedNames = List[Name]()
- def definedNames = definesTerm.toList ++ definesType.toList
- def definedSymbols = List[Symbol]()
+ private lazy val _referencedNames = ImportVarsTraverser(member)
+ def referencedNames = _referencedNames
+ def importedNames = List[Name]()
+ def definedNames = definesTerm.toList ++ definesType.toList
+ def definedSymbols = List[Symbol]()
def extraCodeToEvaluate(req: Request): String = ""
def resultExtractionCode(req: Request): String = ""
@@ -130,6 +131,7 @@ trait MemberHandlers {
}
abstract class MacroHandler(member: DefDef) extends MemberDefHandler(member) {
+ override def referencedNames = super.referencedNames.flatMap(name => List(name.toTermName, name.toTypeName))
override def definesValue = false
override def definesTerm: Option[TermName] = Some(name.toTermName)
override def definesType: Option[TypeName] = None
diff --git a/test/files/neg/macro-bundle-abstract.check b/test/files/neg/macro-bundle-abstract.check
new file mode 100644
index 0000000000..4b07adcc95
--- /dev/null
+++ b/test/files/neg/macro-bundle-abstract.check
@@ -0,0 +1,4 @@
+macro-bundle-abstract.scala:5: error: class Bundle$Bundle needs to be abstract, since method deferred in trait Bundle of type => Int is not defined
+trait Bundle extends Macro {
+ ^
+one error found
diff --git a/test/files/neg/macro-bundle-abstract.scala b/test/files/neg/macro-bundle-abstract.scala
new file mode 100644
index 0000000000..2b302045da
--- /dev/null
+++ b/test/files/neg/macro-bundle-abstract.scala
@@ -0,0 +1,12 @@
+import scala.language.experimental.macros
+import scala.reflect.macros.Macro
+import scala.reflect.macros.Context
+
+trait Bundle extends Macro {
+ def deferred: Int
+ def impl = ???
+}
+
+object Macros {
+ def foo = macro Bundle.impl
+} \ No newline at end of file
diff --git a/test/files/neg/macro-bundle-class.check b/test/files/neg/macro-bundle-class.check
new file mode 100644
index 0000000000..92695390ab
--- /dev/null
+++ b/test/files/neg/macro-bundle-class.check
@@ -0,0 +1,4 @@
+macro-bundle-class.scala:10: error: macro bundles must be monomorphic traits extending scala.reflect.macros.Macro and not implementing its `val c: Context` member
+ def foo = macro Bundle.impl
+ ^
+one error found
diff --git a/test/files/neg/macro-bundle-class.scala b/test/files/neg/macro-bundle-class.scala
new file mode 100644
index 0000000000..4b92cdd40f
--- /dev/null
+++ b/test/files/neg/macro-bundle-class.scala
@@ -0,0 +1,11 @@
+import scala.language.experimental.macros
+import scala.reflect.macros.Macro
+import scala.reflect.macros.Context
+
+class Bundle(val c: Context) extends Macro {
+ def impl = ???
+}
+
+object Macros {
+ def foo = macro Bundle.impl
+} \ No newline at end of file
diff --git a/test/files/neg/macro-bundle-nonmacro.check b/test/files/neg/macro-bundle-nonmacro.check
new file mode 100644
index 0000000000..5a265b5724
--- /dev/null
+++ b/test/files/neg/macro-bundle-nonmacro.check
@@ -0,0 +1,4 @@
+macro-bundle-nonmacro.scala:8: error: not found: value Bundle
+ def foo = Bundle.impl
+ ^
+one error found
diff --git a/test/files/neg/macro-bundle-nonmacro.scala b/test/files/neg/macro-bundle-nonmacro.scala
new file mode 100644
index 0000000000..c7d99f4582
--- /dev/null
+++ b/test/files/neg/macro-bundle-nonmacro.scala
@@ -0,0 +1,9 @@
+import scala.language.experimental.macros
+
+trait Bundle {
+ def impl = ???
+}
+
+object Macros {
+ def foo = Bundle.impl
+} \ No newline at end of file
diff --git a/test/files/neg/macro-bundle-object.check b/test/files/neg/macro-bundle-object.check
new file mode 100644
index 0000000000..e122001427
--- /dev/null
+++ b/test/files/neg/macro-bundle-object.check
@@ -0,0 +1,7 @@
+macro-bundle-object.scala:11: error: macro implementation has wrong shape:
+ required: (c: scala.reflect.macros.Context): c.Expr[Any]
+ found : : Nothing
+number of parameter sections differ
+ def foo = macro Bundle.impl
+ ^
+one error found
diff --git a/test/files/neg/macro-bundle-object.scala b/test/files/neg/macro-bundle-object.scala
new file mode 100644
index 0000000000..98c4238a62
--- /dev/null
+++ b/test/files/neg/macro-bundle-object.scala
@@ -0,0 +1,12 @@
+import scala.language.experimental.macros
+import scala.reflect.macros.Macro
+import scala.reflect.macros.Context
+
+object Bundle extends Macro {
+ val c: Context = ???
+ def impl = ???
+}
+
+object Macros {
+ def foo = macro Bundle.impl
+} \ No newline at end of file
diff --git a/test/files/neg/macro-bundle-polymorphic.check b/test/files/neg/macro-bundle-polymorphic.check
new file mode 100644
index 0000000000..204bd30bca
--- /dev/null
+++ b/test/files/neg/macro-bundle-polymorphic.check
@@ -0,0 +1,10 @@
+macro-bundle-polymorphic.scala:10: error: macro bundles must be monomorphic traits extending scala.reflect.macros.Macro and not implementing its `val c: Context` member
+ def foo = macro Bundle.impl
+ ^
+macro-bundle-polymorphic.scala:11: error: macro bundles must be monomorphic traits extending scala.reflect.macros.Macro and not implementing its `val c: Context` member
+ def foo = macro Bundle[Int].impl
+ ^
+macro-bundle-polymorphic.scala:12: error: macro bundles must be monomorphic traits extending scala.reflect.macros.Macro and not implementing its `val c: Context` member
+ def foo = macro Bundle[Int, Nothing].impl
+ ^
+three errors found
diff --git a/test/files/neg/macro-bundle-polymorphic.scala b/test/files/neg/macro-bundle-polymorphic.scala
new file mode 100644
index 0000000000..0468d841bd
--- /dev/null
+++ b/test/files/neg/macro-bundle-polymorphic.scala
@@ -0,0 +1,13 @@
+import scala.language.experimental.macros
+import scala.reflect.macros.Macro
+import scala.reflect.macros.Context
+
+trait Bundle[T] extends Macro {
+ def impl = ???
+}
+
+object Macros {
+ def foo = macro Bundle.impl
+ def foo = macro Bundle[Int].impl
+ def foo = macro Bundle[Int, Nothing].impl
+} \ No newline at end of file
diff --git a/test/files/neg/macro-bundle-trait.check b/test/files/neg/macro-bundle-trait.check
new file mode 100644
index 0000000000..972788c577
--- /dev/null
+++ b/test/files/neg/macro-bundle-trait.check
@@ -0,0 +1,4 @@
+macro-bundle-trait.scala:11: error: macro bundles must be monomorphic traits extending scala.reflect.macros.Macro and not implementing its `val c: Context` member
+ def foo = macro Bundle.impl
+ ^
+one error found
diff --git a/test/files/neg/macro-bundle-trait.scala b/test/files/neg/macro-bundle-trait.scala
new file mode 100644
index 0000000000..ddc87f6db3
--- /dev/null
+++ b/test/files/neg/macro-bundle-trait.scala
@@ -0,0 +1,12 @@
+import scala.language.experimental.macros
+import scala.reflect.macros.Macro
+import scala.reflect.macros.Context
+
+trait Bundle extends Macro {
+ val c: Context = ???
+ def impl = ???
+}
+
+object Macros {
+ def foo = macro Bundle.impl
+} \ No newline at end of file
diff --git a/test/files/run/macro-bundle-repl.check b/test/files/run/macro-bundle-repl.check
new file mode 100644
index 0000000000..b9c809f037
--- /dev/null
+++ b/test/files/run/macro-bundle-repl.check
@@ -0,0 +1,24 @@
+Type in expressions to have them evaluated.
+Type :help for more information.
+
+scala> import scala.language.experimental.macros
+import scala.language.experimental.macros
+
+scala> import scala.reflect.macros.Macro
+import scala.reflect.macros.Macro
+
+scala> trait Bar extends Macro { def impl = c.literalUnit };def bar = macro Bar.impl
+defined trait Bar
+defined term macro bar: Unit
+
+scala> bar
+
+scala> trait Foo extends Macro { def impl = c.literalUnit }
+defined trait Foo
+
+scala> def foo = macro Foo.impl
+defined term macro foo: Unit
+
+scala> foo
+
+scala>
diff --git a/test/files/run/macro-bundle-repl.scala b/test/files/run/macro-bundle-repl.scala
new file mode 100644
index 0000000000..50783c8cba
--- /dev/null
+++ b/test/files/run/macro-bundle-repl.scala
@@ -0,0 +1,13 @@
+import scala.tools.partest.ReplTest
+
+object Test extends ReplTest {
+ def code = """
+import scala.language.experimental.macros
+import scala.reflect.macros.Macro
+trait Bar extends Macro { def impl = c.literalUnit };def bar = macro Bar.impl
+bar
+trait Foo extends Macro { def impl = c.literalUnit }
+def foo = macro Foo.impl
+foo
+ """
+} \ No newline at end of file
diff --git a/test/files/run/macro-bundle-static.check b/test/files/run/macro-bundle-static.check
new file mode 100644
index 0000000000..37c8eaf27a
--- /dev/null
+++ b/test/files/run/macro-bundle-static.check
@@ -0,0 +1,6 @@
+()
+Int
+()
+true
+IntInt
+true
diff --git a/test/files/run/macro-bundle-static/Impls_Macros_1.scala b/test/files/run/macro-bundle-static/Impls_Macros_1.scala
new file mode 100644
index 0000000000..831dac6df5
--- /dev/null
+++ b/test/files/run/macro-bundle-static/Impls_Macros_1.scala
@@ -0,0 +1,31 @@
+import scala.reflect.macros.Context
+import scala.reflect.macros.Macro
+import scala.language.experimental.macros
+
+object Enclosing {
+ trait Impl extends Macro {
+ def mono = c.literalUnit
+ def poly[T: c.WeakTypeTag] = c.literal(c.weakTypeOf[T].toString)
+ def weird = macro mono
+ }
+}
+
+object Macros {
+ def mono = macro Enclosing.Impl.mono
+ def poly[T] = macro Enclosing.Impl.poly[T]
+}
+
+package pkg {
+ object Enclosing {
+ trait Impl extends Macro {
+ def mono = c.literalTrue
+ def poly[T: c.WeakTypeTag] = c.literal(c.weakTypeOf[T].toString + c.weakTypeOf[T].toString)
+ def weird = macro mono
+ }
+ }
+
+ object Macros {
+ def mono = macro Enclosing.Impl.mono
+ def poly[T] = macro Enclosing.Impl.poly[T]
+ }
+} \ No newline at end of file
diff --git a/test/files/run/macro-bundle-static/Test_2.scala b/test/files/run/macro-bundle-static/Test_2.scala
new file mode 100644
index 0000000000..72160f6ec2
--- /dev/null
+++ b/test/files/run/macro-bundle-static/Test_2.scala
@@ -0,0 +1,8 @@
+object Test extends App {
+ println(Macros.mono)
+ println(Macros.poly[Int])
+ println(new Enclosing.Impl{val c = ???}.weird)
+ println(pkg.Macros.mono)
+ println(pkg.Macros.poly[Int])
+ println(new pkg.Enclosing.Impl{val c = ???}.weird)
+} \ No newline at end of file
diff --git a/test/files/run/macro-bundle-toplevel.check b/test/files/run/macro-bundle-toplevel.check
new file mode 100644
index 0000000000..37c8eaf27a
--- /dev/null
+++ b/test/files/run/macro-bundle-toplevel.check
@@ -0,0 +1,6 @@
+()
+Int
+()
+true
+IntInt
+true
diff --git a/test/files/run/macro-bundle.flags b/test/files/run/macro-bundle-toplevel.flags
index cd66464f2f..cd66464f2f 100644
--- a/test/files/run/macro-bundle.flags
+++ b/test/files/run/macro-bundle-toplevel.flags
diff --git a/test/files/run/macro-bundle/Impls_Macros_1.scala b/test/files/run/macro-bundle-toplevel/Impls_Macros_1.scala
index 3f651c9a43..676935682e 100644
--- a/test/files/run/macro-bundle/Impls_Macros_1.scala
+++ b/test/files/run/macro-bundle-toplevel/Impls_Macros_1.scala
@@ -10,4 +10,17 @@ trait Impl extends Macro {
object Macros {
def mono = macro Impl.mono
def poly[T] = macro Impl.poly[T]
+}
+
+package pkg {
+ trait Impl extends Macro {
+ def mono = c.literalTrue
+ def poly[T: c.WeakTypeTag] = c.literal(c.weakTypeOf[T].toString + c.weakTypeOf[T].toString)
+ def weird = macro mono
+ }
+
+ object Macros {
+ def mono = macro Impl.mono
+ def poly[T] = macro Impl.poly[T]
+ }
} \ No newline at end of file
diff --git a/test/files/run/macro-bundle/Test_2.scala b/test/files/run/macro-bundle-toplevel/Test_2.scala
index 428f809f9d..139cc5bef2 100644
--- a/test/files/run/macro-bundle/Test_2.scala
+++ b/test/files/run/macro-bundle-toplevel/Test_2.scala
@@ -2,4 +2,7 @@ object Test extends App {
println(Macros.mono)
println(Macros.poly[Int])
println(new Impl{val c = ???}.weird)
+ println(pkg.Macros.mono)
+ println(pkg.Macros.poly[Int])
+ println(new pkg.Impl{val c = ???}.weird)
} \ No newline at end of file
diff --git a/test/files/run/macro-bundle.check b/test/files/run/macro-bundle.check
deleted file mode 100644
index 2107454960..0000000000
--- a/test/files/run/macro-bundle.check
+++ /dev/null
@@ -1,3 +0,0 @@
-()
-Int
-()