From e9fc04c4b858dba687bd7268388edc5b9ee0033a Mon Sep 17 00:00:00 2001 From: Nicolas Stucki Date: Tue, 21 Aug 2018 08:51:56 +0200 Subject: [PATCH 1/3] Add back symbols to TASTy reflect --- .../dotc/tastyreflect/SymbolOpsImpl.scala | 15 ++++++++++++ .../dotc/tastyreflect/TastyCoreImpl.scala | 4 +++- .../tools/dotc/tastyreflect/TastyImpl.scala | 2 +- .../tools/dotc/tastyreflect/TreeOpsImpl.scala | 4 +++- library/src/scala/tasty/Tasty.scala | 2 +- .../src/scala/tasty/reflect/SymbolOps.scala | 14 +++++++++++ .../src/scala/tasty/reflect/TastyCore.scala | 7 ++++++ library/src/scala/tasty/reflect/TreeOps.scala | 3 ++- .../scala/tasty/util/TreeAccumulator.scala | 4 ++-- project/scripts/cmdTests | 2 +- ...itions.check => tasty-definitions-1.check} | 0 .../quoted_1.scala | 0 .../quoted_2.scala | 0 tests/run/tasty-definitions-2.check | 2 ++ tests/run/tasty-definitions-2/Macro_1.scala | 23 +++++++++++++++++++ tests/run/tasty-definitions-2/Test_2.scala | 6 +++++ tests/run/tasty-definitions-3.check | 2 ++ tests/run/tasty-definitions-3/Macro_1.scala | 20 ++++++++++++++++ tests/run/tasty-definitions-3/Test_2.scala | 10 ++++++++ 19 files changed, 112 insertions(+), 8 deletions(-) create mode 100644 compiler/src/dotty/tools/dotc/tastyreflect/SymbolOpsImpl.scala create mode 100644 library/src/scala/tasty/reflect/SymbolOps.scala rename tests/run/{tasty-definitions.check => tasty-definitions-1.check} (100%) rename tests/run/{tasty-definitions => tasty-definitions-1}/quoted_1.scala (100%) rename tests/run/{tasty-definitions => tasty-definitions-1}/quoted_2.scala (100%) create mode 100644 tests/run/tasty-definitions-2.check create mode 100644 tests/run/tasty-definitions-2/Macro_1.scala create mode 100644 tests/run/tasty-definitions-2/Test_2.scala create mode 100644 tests/run/tasty-definitions-3.check create mode 100644 tests/run/tasty-definitions-3/Macro_1.scala create mode 100644 tests/run/tasty-definitions-3/Test_2.scala diff --git a/compiler/src/dotty/tools/dotc/tastyreflect/SymbolOpsImpl.scala b/compiler/src/dotty/tools/dotc/tastyreflect/SymbolOpsImpl.scala new file mode 100644 index 000000000000..a3ae96ba5f39 --- /dev/null +++ b/compiler/src/dotty/tools/dotc/tastyreflect/SymbolOpsImpl.scala @@ -0,0 +1,15 @@ +package dotty.tools.dotc.tastyreflect + +import dotty.tools.dotc.ast.tpd +import dotty.tools.dotc.core.Symbols._ + +trait SymbolOpsImpl extends scala.tasty.reflect.SymbolOps with TastyCoreImpl { + + def SymbolasDeco(symbol: Symbol): SymbolasAPI = new SymbolasAPI { + def isEmpty: Boolean = symbol eq NoSymbol + def localContext(implicit ctx: Context): Context = ctx.withOwner(symbol) + def tree(implicit ctx: Context): Option[Definition] = + if (isEmpty) None else Some(FromSymbol.definitionFromSym(symbol)) + } + +} diff --git a/compiler/src/dotty/tools/dotc/tastyreflect/TastyCoreImpl.scala b/compiler/src/dotty/tools/dotc/tastyreflect/TastyCoreImpl.scala index 38e2533ae9b6..1db73141ad25 100644 --- a/compiler/src/dotty/tools/dotc/tastyreflect/TastyCoreImpl.scala +++ b/compiler/src/dotty/tools/dotc/tastyreflect/TastyCoreImpl.scala @@ -50,5 +50,7 @@ trait TastyCoreImpl extends scala.tasty.reflect.TastyCore { type Position = util.SourcePosition type Constant = Constants.Constant - + + type Symbol = core.Symbols.Symbol + } diff --git a/compiler/src/dotty/tools/dotc/tastyreflect/TastyImpl.scala b/compiler/src/dotty/tools/dotc/tastyreflect/TastyImpl.scala index 454208329706..536061cb8b72 100644 --- a/compiler/src/dotty/tools/dotc/tastyreflect/TastyImpl.scala +++ b/compiler/src/dotty/tools/dotc/tastyreflect/TastyImpl.scala @@ -2,4 +2,4 @@ package dotty.tools.dotc.tastyreflect import dotty.tools.dotc.core._ -class TastyImpl(val rootContext: Contexts.Context) extends scala.tasty.Tasty with TastyCoreImpl with CaseDefOpsImpl with ConstantOpsImpl with ContextOpsImpl with IdOpsImpl with ImportSelectorOpsImpl with QuotedOpsImpl with PatternOpsImpl with PositionOpsImpl with PrintersImpl with SignatureOpsImpl with StandardDefinitions with TreeOpsImpl with TypeOrBoundsTreesOpsImpl with TypeOrBoundsOpsImpl +class TastyImpl(val rootContext: Contexts.Context) extends scala.tasty.Tasty with TastyCoreImpl with CaseDefOpsImpl with ConstantOpsImpl with ContextOpsImpl with IdOpsImpl with ImportSelectorOpsImpl with QuotedOpsImpl with PatternOpsImpl with PositionOpsImpl with PrintersImpl with SignatureOpsImpl with StandardDefinitions with SymbolOpsImpl with TreeOpsImpl with TypeOrBoundsTreesOpsImpl with TypeOrBoundsOpsImpl diff --git a/compiler/src/dotty/tools/dotc/tastyreflect/TreeOpsImpl.scala b/compiler/src/dotty/tools/dotc/tastyreflect/TreeOpsImpl.scala index 7ff0fe7d86f7..d0ec292aec85 100644 --- a/compiler/src/dotty/tools/dotc/tastyreflect/TreeOpsImpl.scala +++ b/compiler/src/dotty/tools/dotc/tastyreflect/TreeOpsImpl.scala @@ -13,6 +13,8 @@ trait TreeOpsImpl extends scala.tasty.reflect.TreeOps with TastyCoreImpl with He def TreeDeco(tree: Tree): TreeAPI = new TreeAPI { def pos(implicit ctx: Context): Position = tree.pos + def symbol(implicit ctx: Context): Symbol = tree.symbol + } object IsPackageClause extends IsPackageClauseExtractor { @@ -30,7 +32,7 @@ trait TreeOpsImpl extends scala.tasty.reflect.TreeOps with TastyCoreImpl with He } def PackageClauseDeco(pack: PackageClause): PackageClauseAPI = new PackageClauseAPI { - def definition(implicit ctx: Context): Definition = packageDefFromSym(pack.symbol) + } // ----- Statements ----------------------------------------------- diff --git a/library/src/scala/tasty/Tasty.scala b/library/src/scala/tasty/Tasty.scala index 44da7b06be38..57a832da28ff 100644 --- a/library/src/scala/tasty/Tasty.scala +++ b/library/src/scala/tasty/Tasty.scala @@ -2,4 +2,4 @@ package scala.tasty import scala.tasty.reflect._ -abstract class Tasty extends TastyCore with CaseDefOps with ConstantOps with ContextOps with IdOps with ImportSelectorOps with QuotedOps with PatternOps with PositionOps with Printers with SignatureOps with StandardDefinitions with TreeOps with TypeOrBoundsTreeOps with TypeOrBoundsOps +abstract class Tasty extends TastyCore with CaseDefOps with ConstantOps with ContextOps with IdOps with ImportSelectorOps with QuotedOps with PatternOps with PositionOps with Printers with SignatureOps with StandardDefinitions with SymbolOps with TreeOps with TypeOrBoundsTreeOps with TypeOrBoundsOps diff --git a/library/src/scala/tasty/reflect/SymbolOps.scala b/library/src/scala/tasty/reflect/SymbolOps.scala new file mode 100644 index 000000000000..5598f90e7d81 --- /dev/null +++ b/library/src/scala/tasty/reflect/SymbolOps.scala @@ -0,0 +1,14 @@ +package scala.tasty +package reflect + +/** Tasty reflect symbol */ +trait SymbolOps extends TastyCore { + + trait SymbolasAPI { + def isEmpty: Boolean + def localContext(implicit ctx: Context): Context + def tree(implicit ctx: Context): Option[Definition] + } + implicit def SymbolasDeco(symbol: Symbol): SymbolasAPI + +} diff --git a/library/src/scala/tasty/reflect/TastyCore.scala b/library/src/scala/tasty/reflect/TastyCore.scala index 7cecaf235e77..27391693506b 100644 --- a/library/src/scala/tasty/reflect/TastyCore.scala +++ b/library/src/scala/tasty/reflect/TastyCore.scala @@ -96,6 +96,8 @@ package scala.tasty.reflect * * +- Constant * + * +- Symbol + * * ``` */ trait TastyCore { @@ -158,4 +160,9 @@ trait TastyCore { /** Constant value represented as the constant itself */ type Constant + /** Symbol of a definition. + * Then can be compared with == to know if the definition is the same. + */ + type Symbol + } diff --git a/library/src/scala/tasty/reflect/TreeOps.scala b/library/src/scala/tasty/reflect/TreeOps.scala index 28668323cfe5..253c134859a3 100644 --- a/library/src/scala/tasty/reflect/TreeOps.scala +++ b/library/src/scala/tasty/reflect/TreeOps.scala @@ -5,6 +5,7 @@ trait TreeOps extends TastyCore { trait TreeAPI { def pos(implicit ctx: Context): Position + def symbol(implicit ctx: Context): Symbol } implicit def TreeDeco(tree: Tree): TreeAPI @@ -19,7 +20,7 @@ trait TreeOps extends TastyCore { } trait PackageClauseAPI { - def definition(implicit ctx: Context): Definition + } implicit def PackageClauseDeco(pack: PackageClause): PackageClauseAPI diff --git a/library/src/scala/tasty/util/TreeAccumulator.scala b/library/src/scala/tasty/util/TreeAccumulator.scala index 975efbca9230..a2648d9daa69 100644 --- a/library/src/scala/tasty/util/TreeAccumulator.scala +++ b/library/src/scala/tasty/util/TreeAccumulator.scala @@ -18,7 +18,7 @@ abstract class TreeAccumulator[X, T <: Tasty with Singleton](val tasty: T) { private def foldParents(x: X, trees: Iterable[Parent])(implicit ctx: Context): X = (x /: trees)(foldOverParent) def foldOverTree(x: X, tree: Tree)(implicit ctx: Context): X = { - def localCtx(definition: Definition): Context = definition.localContext + def localCtx(definition: Definition): Context = definition.symbol.localContext tree match { case Term.Ident(_) => x @@ -74,7 +74,7 @@ abstract class TreeAccumulator[X, T <: Tasty with Singleton](val tasty: T) { case Import(expr, selectors) => foldTree(x, expr) case IsPackageClause(clause @ PackageClause(pid, stats)) => - foldTrees(foldTree(x, pid), stats)(localCtx(clause.definition)) + foldTrees(foldTree(x, pid), stats)(clause.symbol.localContext) } } diff --git a/project/scripts/cmdTests b/project/scripts/cmdTests index 1933812f2c17..21473b2c3c7b 100755 --- a/project/scripts/cmdTests +++ b/project/scripts/cmdTests @@ -50,7 +50,7 @@ clear_out "$OUT" grep -qe "def main(args: scala.Array\[scala.Predef.String\]): scala.Unit =" "$tmp" echo "testing scala.quoted.Expr.run from sbt dotr" -"$SBT" ";dotty-compiler-bootstrapped/dotc -with-compiler tests/run-with-compiler/quote-run.scala; dotty-compiler-bootstrapped/dotr -with-compiler Test" > "$tmp" +"$SBT" ";dotty-compiler-bootstrapped/dotc tests/run-with-compiler/quote-run.scala; dotty-compiler-bootstrapped/dotr -with-compiler Test" > "$tmp" grep -qe "val a: scala.Int = 3" "$tmp" diff --git a/tests/run/tasty-definitions.check b/tests/run/tasty-definitions-1.check similarity index 100% rename from tests/run/tasty-definitions.check rename to tests/run/tasty-definitions-1.check diff --git a/tests/run/tasty-definitions/quoted_1.scala b/tests/run/tasty-definitions-1/quoted_1.scala similarity index 100% rename from tests/run/tasty-definitions/quoted_1.scala rename to tests/run/tasty-definitions-1/quoted_1.scala diff --git a/tests/run/tasty-definitions/quoted_2.scala b/tests/run/tasty-definitions-1/quoted_2.scala similarity index 100% rename from tests/run/tasty-definitions/quoted_2.scala rename to tests/run/tasty-definitions-1/quoted_2.scala diff --git a/tests/run/tasty-definitions-2.check b/tests/run/tasty-definitions-2.check new file mode 100644 index 000000000000..e92423eea1ca --- /dev/null +++ b/tests/run/tasty-definitions-2.check @@ -0,0 +1,2 @@ +DefDef("foo", Nil, Nil, TypeTree.Synthetic(), None) +ValDef("bar", TypeTree.Synthetic(), None) diff --git a/tests/run/tasty-definitions-2/Macro_1.scala b/tests/run/tasty-definitions-2/Macro_1.scala new file mode 100644 index 000000000000..cc4870d39e62 --- /dev/null +++ b/tests/run/tasty-definitions-2/Macro_1.scala @@ -0,0 +1,23 @@ +import scala.quoted._ +import scala.tasty._ + +object Foo { + + transparent def inspectBody(i: => Int): String = + ~inspectBodyImpl('(i))(TopLevelSplice.tastyContext) // FIXME infer TopLevelSplice.tastyContext within top level ~ + + def inspectBodyImpl(x: Expr[Int])(implicit tasty: Tasty): Expr[String] = { + import tasty._ + def definitionString(tree: Tree): Expr[String] = tree.symbol.tree match { + case Some(definition) => definition.show.toExpr + case None => '("NO DEFINTION") + } + x.toTasty match { + case Term.Inlined(None, Nil, arg) => definitionString(arg) + case arg => definitionString(arg) // TODO should all by name parameters be in an inline node? + } + } + + def foo: Int = 1 + 2 + val bar: Int = 2 + 3 +} diff --git a/tests/run/tasty-definitions-2/Test_2.scala b/tests/run/tasty-definitions-2/Test_2.scala new file mode 100644 index 000000000000..323560068029 --- /dev/null +++ b/tests/run/tasty-definitions-2/Test_2.scala @@ -0,0 +1,6 @@ +object Test { + def main(args: Array[String]): Unit = { + println(Foo.inspectBody(Foo.foo)) + println(Foo.inspectBody(Foo.bar)) + } +} diff --git a/tests/run/tasty-definitions-3.check b/tests/run/tasty-definitions-3.check new file mode 100644 index 000000000000..e92423eea1ca --- /dev/null +++ b/tests/run/tasty-definitions-3.check @@ -0,0 +1,2 @@ +DefDef("foo", Nil, Nil, TypeTree.Synthetic(), None) +ValDef("bar", TypeTree.Synthetic(), None) diff --git a/tests/run/tasty-definitions-3/Macro_1.scala b/tests/run/tasty-definitions-3/Macro_1.scala new file mode 100644 index 000000000000..02bbd8a351db --- /dev/null +++ b/tests/run/tasty-definitions-3/Macro_1.scala @@ -0,0 +1,20 @@ +import scala.quoted._ +import scala.tasty._ + +object Foo { + + transparent def inspectBody(i: => Int): String = + ~inspectBodyImpl('(i))(TopLevelSplice.tastyContext) // FIXME infer TopLevelSplice.tastyContext within top level ~ + + def inspectBodyImpl(x: Expr[Int])(implicit tasty: Tasty): Expr[String] = { + import tasty._ + def definitionString(tree: Tree): Expr[String] = tree.symbol.tree match { + case Some(definition) => definition.show.toExpr + case None => '("NO DEFINTION") + } + x.toTasty match { + case Term.Inlined(None, Nil, arg) => definitionString(arg) + case arg => definitionString(arg) // TODO should all by name parameters be in an inline node? + } + } +} diff --git a/tests/run/tasty-definitions-3/Test_2.scala b/tests/run/tasty-definitions-3/Test_2.scala new file mode 100644 index 000000000000..9df0c7c1bfe5 --- /dev/null +++ b/tests/run/tasty-definitions-3/Test_2.scala @@ -0,0 +1,10 @@ +object Test { + + def main(args: Array[String]): Unit = { + println(Foo.inspectBody(foo)) + println(Foo.inspectBody(bar)) + } + + def foo: Int = 1 + 2 + val bar: Int = 2 + 3 +} From 9f3afacd28d28c18c3eadc6cb30259bf4d08e24c Mon Sep 17 00:00:00 2001 From: Nicolas Stucki Date: Wed, 22 Aug 2018 14:04:55 +0200 Subject: [PATCH 2/3] Fix typos --- .../src/dotty/tools/dotc/tastyreflect/SymbolOpsImpl.scala | 3 +-- library/src/scala/tasty/reflect/SymbolOps.scala | 4 ++-- 2 files changed, 3 insertions(+), 4 deletions(-) diff --git a/compiler/src/dotty/tools/dotc/tastyreflect/SymbolOpsImpl.scala b/compiler/src/dotty/tools/dotc/tastyreflect/SymbolOpsImpl.scala index a3ae96ba5f39..ae87bcc16b25 100644 --- a/compiler/src/dotty/tools/dotc/tastyreflect/SymbolOpsImpl.scala +++ b/compiler/src/dotty/tools/dotc/tastyreflect/SymbolOpsImpl.scala @@ -1,11 +1,10 @@ package dotty.tools.dotc.tastyreflect -import dotty.tools.dotc.ast.tpd import dotty.tools.dotc.core.Symbols._ trait SymbolOpsImpl extends scala.tasty.reflect.SymbolOps with TastyCoreImpl { - def SymbolasDeco(symbol: Symbol): SymbolasAPI = new SymbolasAPI { + def SymbolDeco(symbol: Symbol): SymbolAPI = new SymbolAPI { def isEmpty: Boolean = symbol eq NoSymbol def localContext(implicit ctx: Context): Context = ctx.withOwner(symbol) def tree(implicit ctx: Context): Option[Definition] = diff --git a/library/src/scala/tasty/reflect/SymbolOps.scala b/library/src/scala/tasty/reflect/SymbolOps.scala index 5598f90e7d81..0ddbd73ba8b1 100644 --- a/library/src/scala/tasty/reflect/SymbolOps.scala +++ b/library/src/scala/tasty/reflect/SymbolOps.scala @@ -4,11 +4,11 @@ package reflect /** Tasty reflect symbol */ trait SymbolOps extends TastyCore { - trait SymbolasAPI { + trait SymbolAPI { def isEmpty: Boolean def localContext(implicit ctx: Context): Context def tree(implicit ctx: Context): Option[Definition] } - implicit def SymbolasDeco(symbol: Symbol): SymbolasAPI + implicit def SymbolDeco(symbol: Symbol): SymbolAPI } From c5399da391cad5b1f646663c2c75380113a96795 Mon Sep 17 00:00:00 2001 From: Nicolas Stucki Date: Wed, 22 Aug 2018 14:07:46 +0200 Subject: [PATCH 3/3] Reformat to avoid long line --- .../tools/dotc/tastyreflect/TastyImpl.scala | 19 ++++++++++++++++++- library/src/scala/tasty/Tasty.scala | 18 +++++++++++++++++- 2 files changed, 35 insertions(+), 2 deletions(-) diff --git a/compiler/src/dotty/tools/dotc/tastyreflect/TastyImpl.scala b/compiler/src/dotty/tools/dotc/tastyreflect/TastyImpl.scala index 536061cb8b72..3ceb2f4fb086 100644 --- a/compiler/src/dotty/tools/dotc/tastyreflect/TastyImpl.scala +++ b/compiler/src/dotty/tools/dotc/tastyreflect/TastyImpl.scala @@ -2,4 +2,21 @@ package dotty.tools.dotc.tastyreflect import dotty.tools.dotc.core._ -class TastyImpl(val rootContext: Contexts.Context) extends scala.tasty.Tasty with TastyCoreImpl with CaseDefOpsImpl with ConstantOpsImpl with ContextOpsImpl with IdOpsImpl with ImportSelectorOpsImpl with QuotedOpsImpl with PatternOpsImpl with PositionOpsImpl with PrintersImpl with SignatureOpsImpl with StandardDefinitions with SymbolOpsImpl with TreeOpsImpl with TypeOrBoundsTreesOpsImpl with TypeOrBoundsOpsImpl +class TastyImpl(val rootContext: Contexts.Context) + extends scala.tasty.Tasty + with TastyCoreImpl + with CaseDefOpsImpl + with ConstantOpsImpl + with ContextOpsImpl + with IdOpsImpl + with ImportSelectorOpsImpl + with QuotedOpsImpl + with PatternOpsImpl + with PositionOpsImpl + with PrintersImpl + with SignatureOpsImpl + with StandardDefinitions + with SymbolOpsImpl + with TreeOpsImpl + with TypeOrBoundsTreesOpsImpl + with TypeOrBoundsOpsImpl diff --git a/library/src/scala/tasty/Tasty.scala b/library/src/scala/tasty/Tasty.scala index 57a832da28ff..ab5a0047ddf7 100644 --- a/library/src/scala/tasty/Tasty.scala +++ b/library/src/scala/tasty/Tasty.scala @@ -2,4 +2,20 @@ package scala.tasty import scala.tasty.reflect._ -abstract class Tasty extends TastyCore with CaseDefOps with ConstantOps with ContextOps with IdOps with ImportSelectorOps with QuotedOps with PatternOps with PositionOps with Printers with SignatureOps with StandardDefinitions with SymbolOps with TreeOps with TypeOrBoundsTreeOps with TypeOrBoundsOps +abstract class Tasty + extends TastyCore + with CaseDefOps + with ConstantOps + with ContextOps + with IdOps + with ImportSelectorOps + with QuotedOps + with PatternOps + with PositionOps + with Printers + with SignatureOps + with StandardDefinitions + with SymbolOps + with TreeOps + with TypeOrBoundsTreeOps + with TypeOrBoundsOps