diff options
author | Martin Odersky <odersky@gmail.com> | 2015-03-04 16:21:45 +0100 |
---|---|---|
committer | Martin Odersky <odersky@gmail.com> | 2015-03-04 16:21:45 +0100 |
commit | b558d6196bb75217acd466bffd59cd4ee339ba27 (patch) | |
tree | 0c79a9828333b53e22715034cccf043b5ff2849a | |
parent | 2bdce25034d50bc7526dc1d1c8f57e9c20e45b60 (diff) | |
download | dotty-b558d6196bb75217acd466bffd59cd4ee339ba27.tar.gz dotty-b558d6196bb75217acd466bffd59cd4ee339ba27.tar.bz2 dotty-b558d6196bb75217acd466bffd59cd4ee339ba27.zip |
Eliminate Throw as a typed Tree
Replace with
<compiler-ops>.throw(exception)
Only leave Throw as an untyped tree.
-rw-r--r-- | src/dotty/tools/backend/jvm/DottyBackendInterface.scala | 4 | ||||
-rw-r--r-- | src/dotty/tools/dotc/ast/Trees.scala | 15 | ||||
-rw-r--r-- | src/dotty/tools/dotc/ast/tpd.scala | 9 | ||||
-rw-r--r-- | src/dotty/tools/dotc/ast/untpd.scala | 10 | ||||
-rw-r--r-- | src/dotty/tools/dotc/core/Definitions.scala | 4 | ||||
-rw-r--r-- | src/dotty/tools/dotc/printing/RefinedPrinter.scala | 7 | ||||
-rw-r--r-- | src/dotty/tools/dotc/transform/TreeTransform.scala | 28 | ||||
-rw-r--r-- | src/dotty/tools/dotc/typer/TypeAssigner.scala | 3 | ||||
-rw-r--r-- | src/dotty/tools/dotc/typer/Typer.scala | 4 |
9 files changed, 27 insertions, 57 deletions
diff --git a/src/dotty/tools/backend/jvm/DottyBackendInterface.scala b/src/dotty/tools/backend/jvm/DottyBackendInterface.scala index 09d0452cf..44377cab4 100644 --- a/src/dotty/tools/backend/jvm/DottyBackendInterface.scala +++ b/src/dotty/tools/backend/jvm/DottyBackendInterface.scala @@ -29,6 +29,8 @@ import Decorators._ import tpd._ import StdNames.nme +case class DummyThrow(expr: tpd.Tree) extends tpd.TermTree + class DottyBackendInterface()(implicit ctx: Context) extends BackendInterface{ trait NonExistentTree extends tpd.Tree type Symbol = Symbols.Symbol @@ -48,7 +50,7 @@ class DottyBackendInterface()(implicit ctx: Context) extends BackendInterface{ type Ident = tpd.Ident type If = tpd.If type ValDef = tpd.ValDef - type Throw = tpd.Throw + type Throw = DummyThrow type Return = tpd.Return type Block = tpd.Block type Typed = tpd.Typed diff --git a/src/dotty/tools/dotc/ast/Trees.scala b/src/dotty/tools/dotc/ast/Trees.scala index 07f8b5525..bd3dec362 100644 --- a/src/dotty/tools/dotc/ast/Trees.scala +++ b/src/dotty/tools/dotc/ast/Trees.scala @@ -513,12 +513,6 @@ object Trees { type ThisTree[-T >: Untyped] = Try[T] } - /** throw expr */ - case class Throw[-T >: Untyped] private[ast] (expr: Tree[T]) - extends TermTree[T] { - type ThisTree[-T >: Untyped] = Throw[T] - } - /** Seq(elems) */ case class SeqLiteral[-T >: Untyped] private[ast] (elems: List[Tree[T]]) extends Tree[T] { @@ -790,7 +784,6 @@ object Trees { type CaseDef = Trees.CaseDef[T] type Return = Trees.Return[T] type Try = Trees.Try[T] - type Throw = Trees.Throw[T] type SeqLiteral = Trees.SeqLiteral[T] type JavaSeqLiteral = Trees.JavaSeqLiteral[T] type TypeTree = Trees.TypeTree[T] @@ -942,10 +935,6 @@ object Trees { case tree: Try if (expr eq tree.expr) && (cases eq tree.cases) && (finalizer eq tree.finalizer) => tree case _ => finalize(tree, untpd.Try(expr, cases, finalizer)) } - def Throw(tree: Tree)(expr: Tree)(implicit ctx: Context): Throw = tree match { - case tree: Throw if (expr eq tree.expr) => tree - case _ => finalize(tree, untpd.Throw(expr)) - } def SeqLiteral(tree: Tree)(elems: List[Tree])(implicit ctx: Context): SeqLiteral = tree match { case tree: JavaSeqLiteral => if (elems eq tree.elems) tree @@ -1097,8 +1086,6 @@ object Trees { cpy.Return(tree)(transform(expr), transformSub(from)) case Try(block, cases, finalizer) => cpy.Try(tree)(transform(block), transformSub(cases), transform(finalizer)) - case Throw(expr) => - cpy.Throw(tree)(transform(expr)) case SeqLiteral(elems) => cpy.SeqLiteral(tree)(transform(elems)) case TypeTree(original) => @@ -1200,8 +1187,6 @@ object Trees { this(this(x, expr), from) case Try(block, handler, finalizer) => this(this(this(x, block), handler), finalizer) - case Throw(expr) => - this(x, expr) case SeqLiteral(elems) => this(x, elems) case TypeTree(original) => diff --git a/src/dotty/tools/dotc/ast/tpd.scala b/src/dotty/tools/dotc/ast/tpd.scala index 77c607ca7..6a3c1d648 100644 --- a/src/dotty/tools/dotc/ast/tpd.scala +++ b/src/dotty/tools/dotc/ast/tpd.scala @@ -117,9 +117,6 @@ object tpd extends Trees.Instance[Type] with TypedTreeInfo { def Try(block: Tree, cases: List[CaseDef], finalizer: Tree)(implicit ctx: Context): Try = ta.assignType(untpd.Try(block, cases, finalizer), block, cases) - def Throw(expr: Tree)(implicit ctx: Context): Throw = - ta.assignType(untpd.Throw(expr)) - def SeqLiteral(elems: List[Tree])(implicit ctx: Context): SeqLiteral = ta.assignType(untpd.SeqLiteral(elems), elems) @@ -252,6 +249,9 @@ object tpd extends Trees.Instance[Type] with TypedTreeInfo { def Annotated(annot: Tree, arg: Tree)(implicit ctx: Context): Annotated = ta.assignType(untpd.Annotated(annot, arg), annot, arg) + + def Throw(expr: Tree)(implicit ctx: Context): Tree = + ref(defn.throwMethod).appliedTo(expr) // ------ Making references ------------------------------------------------------ @@ -493,9 +493,6 @@ object tpd extends Trees.Instance[Type] with TypedTreeInfo { } } - override def Throw(tree: Tree)(expr: Tree)(implicit ctx: Context): Throw = - ta.assignType(untpd.cpy.Throw(tree)(expr)) - override def SeqLiteral(tree: Tree)(elems: List[Tree])(implicit ctx: Context): SeqLiteral = { val tree1 = untpd.cpy.SeqLiteral(tree)(elems) tree match { diff --git a/src/dotty/tools/dotc/ast/untpd.scala b/src/dotty/tools/dotc/ast/untpd.scala index 02ee1eddf..dfff17514 100644 --- a/src/dotty/tools/dotc/ast/untpd.scala +++ b/src/dotty/tools/dotc/ast/untpd.scala @@ -50,6 +50,7 @@ object untpd extends Trees.Instance[Untyped] with UntypedTreeInfo { override def isTerm = trees.isEmpty || trees.head.isTerm override def isType = !isTerm } + case class Throw(expr: Tree) extends TermTree case class WhileDo(cond: Tree, body: Tree) extends TermTree case class DoWhile(body: Tree, cond: Tree) extends TermTree case class ForYield(enums: List[Tree], expr: Tree) extends TermTree @@ -126,7 +127,6 @@ object untpd extends Trees.Instance[Untyped] with UntypedTreeInfo { def CaseDef(pat: Tree, guard: Tree, body: Tree): CaseDef = new CaseDef(pat, guard, body) def Return(expr: Tree, from: Tree): Return = new Return(expr, from) def Try(expr: Tree, cases: List[CaseDef], finalizer: Tree): Try = new Try(expr, cases, finalizer) - def Throw(expr: Tree): Throw = new Throw(expr) def SeqLiteral(elems: List[Tree]): SeqLiteral = new SeqLiteral(elems) def JavaSeqLiteral(elems: List[Tree]): JavaSeqLiteral = new JavaSeqLiteral(elems) def TypeTree(original: Tree): TypeTree = new TypeTree(original) @@ -305,6 +305,10 @@ object untpd extends Trees.Instance[Untyped] with UntypedTreeInfo { case tree: Tuple if (trees eq tree.trees) => tree case _ => untpd.Tuple(trees).withPos(tree.pos) } + def Throw(tree: Tree)(expr: Tree) = tree match { + case tree: Throw if (expr eq tree.expr) => tree + case _ => untpd.Throw(expr).withPos(tree.pos) + } def WhileDo(tree: Tree)(cond: Tree, body: Tree) = tree match { case tree: WhileDo if (cond eq tree.cond) && (body eq tree.body) => tree case _ => untpd.WhileDo(cond, body).withPos(tree.pos) @@ -359,6 +363,8 @@ object untpd extends Trees.Instance[Untyped] with UntypedTreeInfo { cpy.Parens(tree)(transform(t)) case Tuple(trees) => cpy.Tuple(tree)(transform(trees)) + case Throw(expr) => + cpy.Throw(tree)(transform(expr)) case WhileDo(cond, body) => cpy.WhileDo(tree)(transform(cond), transform(body)) case DoWhile(body, cond) => @@ -402,6 +408,8 @@ object untpd extends Trees.Instance[Untyped] with UntypedTreeInfo { this(x, t) case Tuple(trees) => this(x, trees) + case Throw(expr) => + this(x, expr) case WhileDo(cond, body) => this(this(x, cond), body) case DoWhile(body, cond) => diff --git a/src/dotty/tools/dotc/core/Definitions.scala b/src/dotty/tools/dotc/core/Definitions.scala index 67c1f3105..89e4bd371 100644 --- a/src/dotty/tools/dotc/core/Definitions.scala +++ b/src/dotty/tools/dotc/core/Definitions.scala @@ -180,6 +180,10 @@ class Definitions { lazy val dummyApply = newPolyMethod( OpsPackageClass, nme.dummyApply, 1, pt => MethodType(List(FunctionType(Nil, PolyParam(pt, 0))), PolyParam(pt, 0))) + + /** Method representing a throw */ + lazy val throwMethod = newMethod(OpsPackageClass, nme.THROWkw, + MethodType(List(ThrowableType), NothingType)) lazy val NothingClass: ClassSymbol = newCompleteClassSymbol( ScalaPackageClass, tpnme.Nothing, AbstractFinal, List(AnyClass.typeRef)) diff --git a/src/dotty/tools/dotc/printing/RefinedPrinter.scala b/src/dotty/tools/dotc/printing/RefinedPrinter.scala index babf42503..43dbef890 100644 --- a/src/dotty/tools/dotc/printing/RefinedPrinter.scala +++ b/src/dotty/tools/dotc/printing/RefinedPrinter.scala @@ -236,7 +236,12 @@ class RefinedPrinter(_ctx: Context) extends PlainPrinter(_ctx) { case Super(This(name), mix) => optDotPrefix(name) ~ "super" ~ optText(mix)("[" ~ _ ~ "]") case Apply(fun, args) => - toTextLocal(fun) ~ "(" ~ toTextGlobal(args, ", ") ~ ")" + if (fun.hasType && fun.symbol == defn.throwMethod) + changePrec (GlobalPrec) { + "throw " ~ toText(args.head) + } + else + toTextLocal(fun) ~ "(" ~ toTextGlobal(args, ", ") ~ ")" case TypeApply(fun, args) => toTextLocal(fun) ~ "[" ~ toTextGlobal(args, ", ") ~ "]" case Literal(c) => diff --git a/src/dotty/tools/dotc/transform/TreeTransform.scala b/src/dotty/tools/dotc/transform/TreeTransform.scala index c1eb7e72f..ce3e3ce63 100644 --- a/src/dotty/tools/dotc/transform/TreeTransform.scala +++ b/src/dotty/tools/dotc/transform/TreeTransform.scala @@ -83,7 +83,6 @@ object TreeTransforms { def prepareForCaseDef(tree: CaseDef)(implicit ctx: Context) = this def prepareForReturn(tree: Return)(implicit ctx: Context) = this def prepareForTry(tree: Try)(implicit ctx: Context) = this - def prepareForThrow(tree: Throw)(implicit ctx: Context) = this def prepareForSeqLiteral(tree: SeqLiteral)(implicit ctx: Context) = this def prepareForTypeTree(tree: TypeTree)(implicit ctx: Context) = this def prepareForSelectFromTypeTree(tree: SelectFromTypeTree)(implicit ctx: Context) = this @@ -117,7 +116,6 @@ object TreeTransforms { def transformCaseDef(tree: CaseDef)(implicit ctx: Context, info: TransformerInfo): Tree = tree def transformReturn(tree: Return)(implicit ctx: Context, info: TransformerInfo): Tree = tree def transformTry(tree: Try)(implicit ctx: Context, info: TransformerInfo): Tree = tree - def transformThrow(tree: Throw)(implicit ctx: Context, info: TransformerInfo): Tree = tree def transformSeqLiteral(tree: SeqLiteral)(implicit ctx: Context, info: TransformerInfo): Tree = tree def transformTypeTree(tree: TypeTree)(implicit ctx: Context, info: TransformerInfo): Tree = tree def transformSelectFromTypeTree(tree: SelectFromTypeTree)(implicit ctx: Context, info: TransformerInfo): Tree = tree @@ -282,7 +280,6 @@ object TreeTransforms { nxPrepMatch = index(transformations, "prepareForMatch") nxPrepReturn = index(transformations, "prepareForReturn") nxPrepTry = index(transformations, "prepareForTry") - nxPrepThrow = index(transformations, "prepareForThrow") nxPrepSeqLiteral = index(transformations, "prepareForSeqLiteral") nxPrepTypeTree = index(transformations, "prepareForTypeTree") nxPrepSelectFromTypeTree = index(transformations, "prepareForSelectFromTypeTree") @@ -315,7 +312,6 @@ object TreeTransforms { nxTransCaseDef = index(transformations, "transformCaseDef") nxTransReturn = index(transformations, "transformReturn") nxTransTry = index(transformations, "transformTry") - nxTransThrow = index(transformations, "transformThrow") nxTransSeqLiteral = index(transformations, "transformSeqLiteral") nxTransTypeTree = index(transformations, "transformTypeTree") nxTransSelectFromTypeTree = index(transformations, "transformSelectFromTypeTree") @@ -358,7 +354,6 @@ object TreeTransforms { nxPrepCaseDef = indexUpdate(prev.nxPrepCaseDef, changedTransformationClass, transformationIndex, "prepareForCaseDef", copy) nxPrepReturn = indexUpdate(prev.nxPrepReturn, changedTransformationClass, transformationIndex, "prepareForReturn", copy) nxPrepTry = indexUpdate(prev.nxPrepTry, changedTransformationClass, transformationIndex, "prepareForTry", copy) - nxPrepThrow = indexUpdate(prev.nxPrepThrow, changedTransformationClass, transformationIndex, "prepareForThrow", copy) nxPrepSeqLiteral = indexUpdate(prev.nxPrepSeqLiteral, changedTransformationClass, transformationIndex, "prepareForSeqLiteral", copy) nxPrepTypeTree = indexUpdate(prev.nxPrepTypeTree, changedTransformationClass, transformationIndex, "prepareForTypeTree", copy) nxPrepSelectFromTypeTree = indexUpdate(prev.nxPrepSelectFromTypeTree, changedTransformationClass, transformationIndex, "prepareForSelectFromTypeTree", copy) @@ -390,7 +385,6 @@ object TreeTransforms { nxTransCaseDef = indexUpdate(prev.nxTransCaseDef, changedTransformationClass, transformationIndex, "transformCaseDef", copy) nxTransReturn = indexUpdate(prev.nxTransReturn, changedTransformationClass, transformationIndex, "transformReturn", copy) nxTransTry = indexUpdate(prev.nxTransTry, changedTransformationClass, transformationIndex, "transformTry", copy) - nxTransThrow = indexUpdate(prev.nxTransThrow, changedTransformationClass, transformationIndex, "transformThrow", copy) nxTransSeqLiteral = indexUpdate(prev.nxTransSeqLiteral, changedTransformationClass, transformationIndex, "transformSeqLiteral", copy) nxTransTypeTree = indexUpdate(prev.nxTransTypeTree, changedTransformationClass, transformationIndex, "transformTypeTree", copy) nxTransSelectFromTypeTree = indexUpdate(prev.nxTransSelectFromTypeTree, changedTransformationClass, transformationIndex, "transformSelectFromTypeTree", copy) @@ -428,7 +422,6 @@ object TreeTransforms { var nxPrepCaseDef: Array[Int] = _ var nxPrepReturn: Array[Int] = _ var nxPrepTry: Array[Int] = _ - var nxPrepThrow: Array[Int] = _ var nxPrepSeqLiteral: Array[Int] = _ var nxPrepTypeTree: Array[Int] = _ var nxPrepSelectFromTypeTree: Array[Int] = _ @@ -461,7 +454,6 @@ object TreeTransforms { var nxTransCaseDef: Array[Int] = _ var nxTransReturn: Array[Int] = _ var nxTransTry: Array[Int] = _ - var nxTransThrow: Array[Int] = _ var nxTransSeqLiteral: Array[Int] = _ var nxTransTypeTree: Array[Int] = _ var nxTransSelectFromTypeTree: Array[Int] = _ @@ -535,7 +527,6 @@ object TreeTransforms { val prepForCaseDef: Mutator[CaseDef] = (trans, tree, ctx) => trans.prepareForCaseDef(tree)(ctx) val prepForReturn: Mutator[Return] = (trans, tree, ctx) => trans.prepareForReturn(tree)(ctx) val prepForTry: Mutator[Try] = (trans, tree, ctx) => trans.prepareForTry(tree)(ctx) - val prepForThrow: Mutator[Throw] = (trans, tree, ctx) => trans.prepareForThrow(tree)(ctx) val prepForSeqLiteral: Mutator[SeqLiteral] = (trans, tree, ctx) => trans.prepareForSeqLiteral(tree)(ctx) val prepForTypeTree: Mutator[TypeTree] = (trans, tree, ctx) => trans.prepareForTypeTree(tree)(ctx) val prepForSelectFromTypeTree: Mutator[SelectFromTypeTree] = (trans, tree, ctx) => trans.prepareForSelectFromTypeTree(tree)(ctx) @@ -764,17 +755,6 @@ object TreeTransforms { } @tailrec - final private[TreeTransforms] def goThrow(tree: Throw, cur: Int)(implicit ctx: Context, info: TransformerInfo): Tree = { - if (cur < info.transformers.length) { - val trans = info.transformers(cur) - trans.transformThrow(tree)(ctx.withPhase(trans.treeTransformPhase), info) match { - case t: Throw => goThrow(t, info.nx.nxTransThrow(cur + 1)) - case t => transformSingle(t, cur + 1) - } - } else tree - } - - @tailrec final private[TreeTransforms] def goSeqLiteral(tree: SeqLiteral, cur: Int)(implicit ctx: Context, info: TransformerInfo): Tree = { if (cur < info.transformers.length) { val trans = info.transformers(cur) @@ -943,7 +923,6 @@ object TreeTransforms { case tree: CaseDef => goCaseDef(tree, info.nx.nxTransCaseDef(cur)) case tree: Return => goReturn(tree, info.nx.nxTransReturn(cur)) case tree: Try => goTry(tree, info.nx.nxTransTry(cur)) - case tree: Throw => goThrow(tree, info.nx.nxTransThrow(cur)) case tree: SeqLiteral => goSeqLiteral(tree, info.nx.nxTransLiteral(cur)) case tree: TypeTree => goTypeTree(tree, info.nx.nxTransTypeTree(cur)) case tree: Alternative => goAlternative(tree, info.nx.nxTransAlternative(cur)) @@ -1157,13 +1136,6 @@ object TreeTransforms { val finalizer = transform(tree.finalizer, mutatedInfo, cur) goTry(cpy.Try(tree)(block, cases1, finalizer), mutatedInfo.nx.nxTransTry(cur)) } - case tree: Throw => - implicit val mutatedInfo: TransformerInfo = mutateTransformers(info, prepForThrow, info.nx.nxPrepThrow, tree, cur) - if (mutatedInfo eq null) tree - else { - val expr = transform(tree.expr, mutatedInfo, cur) - goThrow(cpy.Throw(tree)(expr), mutatedInfo.nx.nxTransThrow(cur)) - } case tree: SeqLiteral => implicit val mutatedInfo: TransformerInfo = mutateTransformers(info, prepForSeqLiteral, info.nx.nxPrepSeqLiteral, tree, cur) if (mutatedInfo eq null) tree diff --git a/src/dotty/tools/dotc/typer/TypeAssigner.scala b/src/dotty/tools/dotc/typer/TypeAssigner.scala index f4b0ef4f2..f85c3a577 100644 --- a/src/dotty/tools/dotc/typer/TypeAssigner.scala +++ b/src/dotty/tools/dotc/typer/TypeAssigner.scala @@ -304,9 +304,6 @@ trait TypeAssigner { else tree.withType(ctx.typeComparer.lub(expr.tpe :: cases.tpes)) } - def assignType(tree: untpd.Throw)(implicit ctx: Context) = - tree.withType(defn.NothingType) - def assignType(tree: untpd.SeqLiteral, elems: List[Tree])(implicit ctx: Context) = tree match { case tree: JavaSeqLiteral => tree.withType(defn.ArrayType(ctx.typeComparer.lub(elems.tpes).widen)) diff --git a/src/dotty/tools/dotc/typer/Typer.scala b/src/dotty/tools/dotc/typer/Typer.scala index 76a9dbfdc..b3ac0f50a 100644 --- a/src/dotty/tools/dotc/typer/Typer.scala +++ b/src/dotty/tools/dotc/typer/Typer.scala @@ -735,9 +735,9 @@ class Typer extends Namer with TypeAssigner with Applications with Implicits wit assignType(cpy.Try(tree)(expr1, cases1, finalizer1), expr1, cases1) } - def typedThrow(tree: untpd.Throw)(implicit ctx: Context): Throw = track("typedThrow") { + def typedThrow(tree: untpd.Throw)(implicit ctx: Context): Tree = track("typedThrow") { val expr1 = typed(tree.expr, defn.ThrowableType) - assignType(cpy.Throw(tree)(expr1)) + Throw(expr1).withPos(tree.pos) } def typedSeqLiteral(tree: untpd.SeqLiteral, pt: Type)(implicit ctx: Context): SeqLiteral = track("typedSeqLiteral") { |