diff options
Diffstat (limited to 'src/main/scala/scala/async/internal/AsyncTransform.scala')
-rw-r--r-- | src/main/scala/scala/async/internal/AsyncTransform.scala | 89 |
1 files changed, 41 insertions, 48 deletions
diff --git a/src/main/scala/scala/async/internal/AsyncTransform.scala b/src/main/scala/scala/async/internal/AsyncTransform.scala index ca53ff1..cf9dd1c 100644 --- a/src/main/scala/scala/async/internal/AsyncTransform.scala +++ b/src/main/scala/scala/async/internal/AsyncTransform.scala @@ -3,7 +3,9 @@ package scala.async.internal trait AsyncTransform { self: AsyncMacro => - import global._ + import c.universe._ + import c.internal._ + import decorators._ val asyncBase: AsyncBase @@ -13,7 +15,7 @@ trait AsyncTransform { // We annotate the type of the whole expression as `T @uncheckedBounds` so as not to introduce // warnings about non-conformant LUBs. See SI-7694 // This implicit propagates the annotated type in the type tag. - implicit val uncheckedBoundsResultTag: WeakTypeTag[T] = WeakTypeTag[T](rootMirror, FixedMirrorTypeCreator(rootMirror, uncheckedBounds(resultType.tpe))) + implicit val uncheckedBoundsResultTag: WeakTypeTag[T] = c.WeakTypeTag[T](uncheckedBounds(resultType.tpe)) reportUnsupportedAwaits(body) @@ -55,7 +57,7 @@ trait AsyncTransform { val template = Template(List(tryToUnit, typeOf[() => Unit]).map(TypeTree(_)), emptyValDef, body) val t = ClassDef(NoMods, name.stateMachineT, Nil, template) - callSiteTyper.typedPos(macroPos)(Block(t :: Nil, Literal(Constant(())))) + typingTransform(atPos(macroPos)(Block(t :: Nil, Literal(Constant(())))))((tree, api) => api.typecheck(tree)) t } @@ -78,9 +80,9 @@ trait AsyncTransform { val fieldSym = fld.symbol Block( List( - asyncBase.nullOut(global)(Expr[String](Literal(Constant(fieldSym.name.toString))), Expr[Any](Ident(fieldSym))).tree + asyncBase.nullOut(c.universe)(c.Expr[String](Literal(Constant(fieldSym.name.toString))), c.Expr[Any](Ident(fieldSym))).tree ), - Assign(gen.mkAttributedStableRef(fieldSym.owner.thisType, fieldSym), gen.mkZero(fieldSym.info)) + Assign(gen.mkAttributedStableRef(thisType(fieldSym.owner), fieldSym), gen.mkZero(fieldSym.info)) ) } val asyncState = asyncBlock.asyncStates.find(_.state == state).get @@ -102,7 +104,7 @@ trait AsyncTransform { ValDef(NoMods, name.stateMachine, TypeTree(), Apply(Select(New(Ident(stateMachine.symbol)), nme.CONSTRUCTOR), Nil)), futureSystemOps.spawn(Apply(selectStateMachine(name.apply), Nil), selectStateMachine(name.execContext)) ), - futureSystemOps.promiseToFuture(Expr[futureSystem.Prom[T]](selectStateMachine(name.result))).tree) + futureSystemOps.promiseToFuture(c.Expr[futureSystem.Prom[T]](selectStateMachine(name.result))).tree) } val isSimple = asyncBlock.asyncStates.size == 1 @@ -121,7 +123,7 @@ trait AsyncTransform { } AsyncUtils.vprintln(s"In file '$location':") - AsyncUtils.vprintln(s"${macroApplication}") + AsyncUtils.vprintln(s"${c.macroApplication}") AsyncUtils.vprintln(s"ANF transform expands to:\n $anfTree") states foreach (s => AsyncUtils.vprintln(s)) } @@ -141,79 +143,70 @@ trait AsyncTransform { liftedSyms.foreach { sym => if (sym != null) { - sym.owner = stateMachineClass + sym.setOwner(stateMachineClass) if (sym.isModule) - sym.moduleClass.owner = stateMachineClass + sym.asModule.moduleClass.setOwner(stateMachineClass) } } // Replace the ValDefs in the splicee with Assigns to the corresponding lifted // fields. Similarly, replace references to them with references to the field. // // This transform will only be run on the RHS of `def foo`. - class UseFields extends MacroTypingTransformer { - override def transform(tree: Tree): Tree = tree match { - case _ if currentOwner == stateMachineClass => - super.transform(tree) - case ValDef(_, _, _, rhs) if liftedSyms(tree.symbol) => - atOwner(currentOwner) { - val fieldSym = tree.symbol - val set = Assign(gen.mkAttributedStableRef(fieldSym.owner.thisType, fieldSym), transform(rhs)) - changeOwner(set, tree.symbol, currentOwner) - localTyper.typedPos(tree.pos)(set) - } - case _: DefTree if liftedSyms(tree.symbol) => - EmptyTree - case Ident(name) if liftedSyms(tree.symbol) => + val useFields: (Tree, TypingTransformApi) => Tree = (tree, api) => tree match { + case _ if api.currentOwner == stateMachineClass => + api.default(tree) + case ValDef(_, _, _, rhs) if liftedSyms(tree.symbol) => + api.atOwner(api.currentOwner) { val fieldSym = tree.symbol - atPos(tree.pos) { - gen.mkAttributedStableRef(fieldSym.owner.thisType, fieldSym).setType(tree.tpe) - } - case _ => - super.transform(tree) - } + val set = Assign(gen.mkAttributedStableRef(thisType(fieldSym.owner.asClass), fieldSym), api.recur(rhs)) + set.changeOwner(tree.symbol, api.currentOwner) + api.typecheck(atPos(tree.pos)(set)) + } + case _: DefTree if liftedSyms(tree.symbol) => + EmptyTree + case Ident(name) if liftedSyms(tree.symbol) => + val fieldSym = tree.symbol + atPos(tree.pos) { + gen.mkAttributedStableRef(thisType(fieldSym.owner.asClass), fieldSym).setType(tree.tpe) + } + case _ => + api.default(tree) } val liftablesUseFields = liftables.map { case vd: ValDef => vd - case x => - val useField = new UseFields() - //.substituteSymbols(fromSyms, toSyms) - useField.atOwner(stateMachineClass)(useField.transform(x)) + case x => typingTransform(x, stateMachineClass)(useFields) } - tree.children.foreach { - t => - new ChangeOwnerAndModuleClassTraverser(callSiteTyper.context.owner, tree.symbol).traverse(t) - } + tree.children.foreach(_.changeOwner(enclosingOwner, tree.symbol)) val treeSubst = tree /* Fixes up DefDef: use lifted fields in `body` */ - def fixup(dd: DefDef, body: Tree, ctx: analyzer.Context): Tree = { + def fixup(dd: DefDef, body: Tree, api: TypingTransformApi): Tree = { val spliceeAnfFixedOwnerSyms = body - val useField = new UseFields() - val newRhs = useField.atOwner(dd.symbol)(useField.transform(spliceeAnfFixedOwnerSyms)) - val typer = global.analyzer.newTyper(ctx.make(dd, dd.symbol)) - treeCopy.DefDef(dd, dd.mods, dd.name, dd.tparams, dd.vparamss, dd.tpt, typer.typed(newRhs)) + val newRhs = typingTransform(spliceeAnfFixedOwnerSyms, dd.symbol)(useFields) + val newRhsTyped = api.atOwner(dd, dd.symbol)(api.typecheck(newRhs)) + treeCopy.DefDef(dd, dd.mods, dd.name, dd.tparams, dd.vparamss, dd.tpt, newRhsTyped) } liftablesUseFields.foreach(t => if (t.symbol != null) stateMachineClass.info.decls.enter(t.symbol)) val result0 = transformAt(treeSubst) { case t@Template(parents, self, stats) => - (ctx: analyzer.Context) => { + (api: TypingTransformApi) => { treeCopy.Template(t, parents, self, liftablesUseFields ++ stats) } } val result = transformAt(result0) { case dd@DefDef(_, name.apply, _, List(List(_)), _, _) if dd.symbol.owner == stateMachineClass => - (ctx: analyzer.Context) => - val typedTree = fixup(dd, changeOwner(applyBody, callSiteTyper.context.owner, dd.symbol), ctx) + (api: TypingTransformApi) => + val typedTree = fixup(dd, applyBody.changeOwner(enclosingOwner, dd.symbol), api) typedTree case dd@DefDef(_, name.resume, _, _, _, _) if dd.symbol.owner == stateMachineClass => - (ctx: analyzer.Context) => - val changed = changeOwner(resumeBody, callSiteTyper.context.owner, dd.symbol) - val res = fixup(dd, changed, ctx) + (api: TypingTransformApi) => + val changed = resumeBody.changeOwner(enclosingOwner, dd.symbol) + val res = fixup(dd, changed, api) res } result |