Skip to content

Commit 48c6d83

Browse files
committed
Implement TASTy reflect constructors
1 parent fcc35d2 commit 48c6d83

22 files changed

+1042
-118
lines changed

compiler/src/dotty/tools/dotc/ast/Trees.scala

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -975,13 +975,13 @@ object Trees {
975975
* so that they selectively retype themselves. Retyping needs a context.
976976
*/
977977
abstract class TreeCopier {
978-
def postProcess(tree: Tree, copied: untpd.Tree): copied.ThisTree[T]
979-
def postProcess(tree: Tree, copied: untpd.MemberDef): copied.ThisTree[T]
978+
protected def postProcess(tree: Tree, copied: untpd.Tree): copied.ThisTree[T]
979+
protected def postProcess(tree: Tree, copied: untpd.MemberDef): copied.ThisTree[T]
980980

981-
def finalize(tree: Tree, copied: untpd.Tree): copied.ThisTree[T] =
981+
protected def finalize(tree: Tree, copied: untpd.Tree): copied.ThisTree[T] =
982982
postProcess(tree, copied.withPos(tree.pos).withAttachmentsFrom(tree))
983983

984-
def finalize(tree: Tree, copied: untpd.MemberDef): copied.ThisTree[T] =
984+
protected def finalize(tree: Tree, copied: untpd.MemberDef): copied.ThisTree[T] =
985985
postProcess(tree, copied.withPos(tree.pos).withAttachmentsFrom(tree))
986986

987987
def Ident(tree: Tree)(name: Name): Ident = tree match {

compiler/src/dotty/tools/dotc/tastyreflect/CaseDefOpsImpl.scala

Lines changed: 13 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,6 @@
11
package dotty.tools.dotc.tastyreflect
22

3+
import dotty.tools.dotc.ast.tpd
34

45
trait CaseDefOpsImpl extends scala.tasty.reflect.CaseDefOps with CoreImpl with Helpers {
56

@@ -10,6 +11,12 @@ trait CaseDefOpsImpl extends scala.tasty.reflect.CaseDefOps with CoreImpl with H
1011
}
1112

1213
object CaseDef extends CaseDefModule {
14+
def apply(pattern: Pattern, guard: Option[Term], body: Term)(implicit ctx: Context): CaseDef =
15+
tpd.CaseDef(pattern, guard.getOrElse(tpd.EmptyTree), body)
16+
17+
def copy(original: CaseDef)(pattern: Pattern, guard: Option[Term], body: Term)(implicit ctx: Context): CaseDef =
18+
tpd.cpy.CaseDef(original)(pattern, guard.getOrElse(tpd.EmptyTree), body)
19+
1320
def unapply(x: CaseDef): Some[(Pattern, Option[Term], Term)] = Some(x.pat, optional(x.guard), x.body)
1421
}
1522

@@ -19,6 +26,12 @@ trait CaseDefOpsImpl extends scala.tasty.reflect.CaseDefOps with CoreImpl with H
1926
}
2027

2128
object TypeCaseDef extends TypeCaseDefModule {
29+
def apply(pattern: TypeTree, body: TypeTree)(implicit ctx: Context): TypeCaseDef =
30+
tpd.CaseDef(pattern, tpd.EmptyTree, body)
31+
32+
def copy(original: TypeCaseDef)(pattern: TypeTree, body: TypeTree)(implicit ctx: Context): TypeCaseDef =
33+
tpd.cpy.CaseDef(original)(pattern, tpd.EmptyTree, body)
34+
2235
def unapply(x: TypeCaseDef): Some[(TypeTree, TypeTree)] = Some((x.pat, x.body))
2336
}
2437
}

compiler/src/dotty/tools/dotc/tastyreflect/CoreImpl.scala

Lines changed: 7 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -26,8 +26,9 @@ trait CoreImpl extends scala.tasty.reflect.Core {
2626
type Term = tpd.Tree
2727
val Term: TermCoreModuleImpl
2828
trait TermCoreModuleImpl extends TermCoreModule {
29-
type Ident = tpd.Ident
30-
type Select = tpd.Select
29+
type Ref = tpd.RefTree
30+
type Ident = tpd.Ident
31+
type Select = tpd.Select
3132
type Literal = tpd.Literal
3233
type This = tpd.This
3334
type New = tpd.New
@@ -56,8 +57,8 @@ trait CoreImpl extends scala.tasty.reflect.Core {
5657
type Pattern = tpd.Tree
5758
type Value = tpd.Tree
5859
type Bind = tpd.Bind
59-
type Unapply = tpd.Tree
60-
type Alternative = tpd.Alternative
60+
type Unapply = tpd.UnApply
61+
type Alternatives = tpd.Alternative
6162
type TypeTest = tpd.Typed
6263

6364
type TypeOrBoundsTree = tpd.Tree
@@ -77,8 +78,8 @@ trait CoreImpl extends scala.tasty.reflect.Core {
7778
type MatchType = tpd.MatchTypeTree
7879
type ByName = tpd.ByNameTypeTree
7980
type LambdaTypeTree = tpd.LambdaTypeTree
80-
type Bind = tpd.Bind
81-
type Block = tpd.Block
81+
type TypeBind = tpd.Bind
82+
type TypeBlock = tpd.Block
8283
}
8384
type TypeBoundsTree = tpd.TypeBoundsTree
8485
type WildcardType = tpd.TypeTree

compiler/src/dotty/tools/dotc/tastyreflect/PatternOpsImpl.scala

Lines changed: 99 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -1,10 +1,36 @@
11
package dotty.tools.dotc.tastyreflect
22

3-
import dotty.tools.dotc.ast.{Trees, tpd}
3+
import dotty.tools.dotc.ast.{Trees, tpd, untpd}
4+
import dotty.tools.dotc.core.Contexts
45
import dotty.tools.dotc.core.Decorators._
6+
import dotty.tools.dotc.core.StdNames.nme
57

68
trait PatternOpsImpl extends scala.tasty.reflect.PatternOps with CoreImpl {
79

10+
def ValueDeco(value: Value): Pattern.ValueAPI = new Pattern.ValueAPI {
11+
def value(implicit ctx: Context): Term = value
12+
}
13+
def BindDeco(bind: Bind): Pattern.BindAPI = new Pattern.BindAPI {
14+
def name(implicit ctx: Context): String = bind.name.toString
15+
def pattern(implicit ctx: Context): Pattern = bind.body
16+
}
17+
def UnapplyDeco(unapply: Unapply): Pattern.UnapplyAPI = new Pattern.UnapplyAPI {
18+
def fun(implicit ctx: Context): Term = unapply.fun
19+
def implicits(implicit ctx: Context): List[Term] = unapply.implicits
20+
def patterns(implicit ctx: Context): List[Pattern] = effectivePatterns(unapply.patterns)
21+
22+
private def effectivePatterns(patterns: List[Pattern]): List[Pattern] = patterns match {
23+
case patterns0 :+ Trees.SeqLiteral(elems, _) => patterns0 ::: elems
24+
case _ => patterns
25+
}
26+
}
27+
def AlternativeDeco(alternatives: Alternatives): Pattern.AlternativesAPI = new Pattern.AlternativesAPI {
28+
def patterns(implicit ctx: Context): List[Pattern] = alternatives.trees
29+
}
30+
def TypeTestDeco(typeTest: TypeTest): Pattern.TypeTestAPI = new Pattern.TypeTestAPI {
31+
def tpt(implicit ctx: Context): TypeTree = typeTest.tpt
32+
}
33+
834
// ----- Patterns -------------------------------------------------
935

1036
def PatternDeco(pattern: Pattern): PatternAPI = new PatternAPI {
@@ -14,45 +40,106 @@ trait PatternOpsImpl extends scala.tasty.reflect.PatternOps with CoreImpl {
1440

1541
object Pattern extends PatternModule {
1642

17-
object Value extends ValueModule {
18-
def unapply(x: Pattern)(implicit ctx: Context): Option[Term] = x match {
43+
object IsValue extends IsValueModule {
44+
def unapply(pattern: Pattern)(implicit ctx: Context): Option[Value] = pattern match {
1945
case lit: tpd.Literal => Some(lit)
2046
case ref: tpd.RefTree if ref.isTerm => Some(ref)
2147
case ths: tpd.This => Some(ths)
2248
case _ => None
2349
}
2450
}
2551

52+
object Value extends ValueModule {
53+
def apply(term: Term)(implicit ctx: Context): Value = term match {
54+
case lit: tpd.Literal => lit
55+
case ref: tpd.RefTree if ref.isTerm => ref
56+
case ths: tpd.This => ths
57+
}
58+
def copy(original: Value)(term: Term)(implicit ctx: Context): Value = term match {
59+
case lit: tpd.Literal => tpd.cpy.Literal(original)(lit.const)
60+
case ref: tpd.RefTree if ref.isTerm => tpd.cpy.Ref(original.asInstanceOf[tpd.RefTree])(ref.name)
61+
case ths: tpd.This => tpd.cpy.This(original)(ths.qual)
62+
}
63+
def unapply(x: Pattern)(implicit ctx: Context): Option[Term] = IsValue.unapply(x)
64+
}
65+
66+
object IsBind extends IsBindModule {
67+
def unapply(x: Pattern)(implicit ctx: Context): Option[Bind] = x match {
68+
case x: tpd.Bind if x.name.isTermName => Some(x)
69+
case _ => None
70+
}
71+
}
72+
2673
object Bind extends BindModule {
27-
def unapply(x: Pattern)(implicit ctx: Context): Option[(String, Pattern)] = x match {
28-
case x: tpd.Bind if x.name.isTermName => Some(x.name.toString, x.body)
74+
def apply(name: String, pattern: Pattern)(implicit ctx: Context): Bind = ???
75+
76+
def copy(original: Bind)(name: String, pattern: Pattern)(implicit ctx: Context): Bind =
77+
tpd.cpy.Bind(original)(name.toTermName, pattern)
78+
79+
def unapply(pattern: Pattern)(implicit ctx: Context): Option[(String, Pattern)] = pattern match {
80+
case IsBind(pattern) => Some((pattern.name.toString, pattern.body))
81+
case _ => None
82+
}
83+
}
84+
85+
object IsUnapply extends IsUnapplyModule {
86+
def unapply(pattern: Pattern)(implicit ctx: Context): Option[Unapply] = pattern match {
87+
case pattern @ Trees.UnApply(_, _, _) => Some(pattern)
88+
case Trees.Typed(pattern @ Trees.UnApply(_, _, _), _) => Some(pattern)
2989
case _ => None
3090
}
3191
}
3292

3393
object Unapply extends UnapplyModule {
94+
def apply(fun: Term, implicits: List[Term], patterns: List[Pattern])(implicit ctx: Context): Unapply = ???
95+
96+
def copy(original: Unapply)(fun: Term, implicits: List[Term], patterns: List[Pattern])(implicit ctx: Context): Unapply =
97+
tpd.cpy.UnApply(original)(fun, implicits, patterns)
98+
3499
def unapply(x: Pattern)(implicit ctx: Context): Option[(Term, List[Term], List[Pattern])] = x match {
35-
case Trees.UnApply(fun, implicits, patterns) => Some((fun, implicits, effectivePatterns(patterns)))
36-
case Trees.Typed(Trees.UnApply(fun, implicits, patterns), _) => Some((fun, implicits, effectivePatterns(patterns)))
100+
case IsUnapply(x) => Some((x.fun, x.implicits, UnapplyDeco(x).patterns))
37101
case _ => None
38102
}
39-
private def effectivePatterns(patterns: List[Pattern]): List[Pattern] = patterns match {
40-
case patterns0 :+ Trees.SeqLiteral(elems, _) => patterns0 ::: elems
41-
case _ => patterns
103+
}
104+
105+
object IsAlternatives extends IsAlternativesModule {
106+
def unapply(pattern: Pattern)(implicit ctx: Context): Option[Alternatives] = pattern match {
107+
case pattern: tpd.Alternative => Some(pattern)
108+
case _ => None
42109
}
43110
}
44111

45-
object Alternative extends AlternativeModule {
112+
object Alternatives extends AlternativesModule {
113+
def apply(patterns: List[Pattern])(implicit ctx: Context): Alternatives =
114+
tpd.Alternative(patterns)
115+
116+
def copy(original: Alternatives)(patterns: List[Pattern])(implicit ctx: Context): Alternatives =
117+
tpd.cpy.Alternative(original)(patterns)
118+
46119
def unapply(x: Pattern)(implicit ctx: Context): Option[List[Pattern]] = x match {
47120
case x: tpd.Alternative => Some(x.trees)
48121
case _ => None
49122
}
50123
}
51124

125+
object IsTypeTest extends IsTypeTestModule {
126+
def unapply(pattern: Pattern)(implicit ctx: Context): Option[TypeTest] = pattern match {
127+
case Trees.Typed(_: tpd.UnApply, _) => None
128+
case pattern: tpd.Typed => Some(pattern)
129+
case _ => None
130+
}
131+
}
132+
52133
object TypeTest extends TypeTestModule {
134+
def apply(tpt: TypeTree)(implicit ctx: Context): TypeTest =
135+
tpd.Typed(untpd.Ident(nme.WILDCARD).withType(tpt.tpe), tpt)
136+
137+
def copy(original: TypeTest)(tpt: TypeTree)(implicit ctx: Context): TypeTest =
138+
tpd.cpy.Typed(original)(untpd.Ident(nme.WILDCARD).withType(tpt.tpe), tpt)
139+
53140
def unapply(x: Pattern)(implicit ctx: Context): Option[TypeTree] = x match {
54141
case Trees.Typed(Trees.UnApply(_, _, _), _) => None
55-
case Trees.Typed(_, tpt) => Some(tpt)
142+
case Trees.Typed(expr, tpt) => Some(tpt)
56143
case _ => None
57144
}
58145
}

0 commit comments

Comments
 (0)