Skip to content

Commit 2729819

Browse files
Merge pull request #3143 from dotty-staging/ycheck-patterns
Update ReTyper to Ycheck patterns & inline fixes
2 parents 23c6cef + 66874ed commit 2729819

13 files changed

+96
-19
lines changed

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

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -519,8 +519,8 @@ trait TypedTreeInfo extends TreeInfo[Type] { self: Trees.Instance[Type] =>
519519
val (meth, targs, argss) = decomposeCall(fn)
520520
(meth, targs, argss :+ args)
521521
case TypeApply(fn, targs) =>
522-
val (meth, Nil, Nil) = decomposeCall(fn)
523-
(meth, targs, Nil)
522+
val (meth, targss, args) = decomposeCall(fn)
523+
(meth, targs ++ targss, args)
524524
case _ =>
525525
(tree, Nil, Nil)
526526
}

compiler/src/dotty/tools/dotc/transform/TreeChecker.scala

Lines changed: 1 addition & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -261,9 +261,6 @@ class TreeChecker extends Phase with SymTransformer {
261261

262262
override def typedUnadapted(tree: untpd.Tree, pt: Type)(implicit ctx: Context): tpd.Tree = {
263263
val res = tree match {
264-
case _: untpd.UnApply =>
265-
// can't recheck patterns
266-
tree.asInstanceOf[tpd.Tree]
267264
case _: untpd.TypedSplice | _: untpd.Thicket | _: EmptyValDef[_] =>
268265
super.typedUnadapted(tree)
269266
case _ if tree.isType =>
@@ -291,7 +288,7 @@ class TreeChecker extends Phase with SymTransformer {
291288
}
292289

293290
def checkNotRepeated(tree: Tree)(implicit ctx: Context): tree.type = {
294-
def allowedRepeated = (tree.symbol.flags is Case) && tree.tpe.widen.isRepeatedParam
291+
def allowedRepeated = tree.tpe.widen.isRepeatedParam
295292

296293
assert(!tree.tpe.widen.isRepeatedParam || allowedRepeated, i"repeated parameter type not allowed here: $tree")
297294
tree

compiler/src/dotty/tools/dotc/typer/Applications.scala

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -957,9 +957,10 @@ trait Applications extends Compatibility { self: Typer with Dynamic =>
957957
}
958958
val dummyArg = dummyTreeOfType(ownType)
959959
val unapplyApp = typedExpr(untpd.TypedSplice(Apply(unapplyFn, dummyArg :: Nil)))
960-
val unapplyImplicits = unapplyApp match {
960+
def unapplyImplicits(unapp: Tree): List[Tree] = unapp match {
961961
case Apply(Apply(unapply, `dummyArg` :: Nil), args2) => assert(args2.nonEmpty); args2
962962
case Apply(unapply, `dummyArg` :: Nil) => Nil
963+
case Inlined(u, _, _) => unapplyImplicits(u)
963964
}
964965

965966
var argTypes = unapplyArgs(unapplyApp.tpe, unapplyFn, args, tree.pos)
@@ -983,7 +984,7 @@ trait Applications extends Compatibility { self: Typer with Dynamic =>
983984
List.fill(argTypes.length - args.length)(WildcardType)
984985
}
985986
val unapplyPatterns = (bunchedArgs, argTypes).zipped map (typed(_, _))
986-
val result = assignType(cpy.UnApply(tree)(unapplyFn, unapplyImplicits, unapplyPatterns), ownType)
987+
val result = assignType(cpy.UnApply(tree)(unapplyFn, unapplyImplicits(unapplyApp), unapplyPatterns), ownType)
987988
unapp.println(s"unapply patterns = $unapplyPatterns")
988989
if ((ownType eq selType) || ownType.isError) result
989990
else tryWithClassTag(Typed(result, TypeTree(ownType)), selType)

compiler/src/dotty/tools/dotc/typer/Inliner.scala

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -478,7 +478,7 @@ class Inliner(call: tpd.Tree, rhs: tpd.Tree)(implicit ctx: Context) {
478478
paramProxy.get(tree.tpe) match {
479479
case Some(t) if tree.isTerm && t.isSingleton => singleton(t).withPos(tree.pos)
480480
case Some(t) if tree.isType => TypeTree(t).withPos(tree.pos)
481-
case None => tree
481+
case _ => tree
482482
}
483483
case _ => tree
484484
}}

compiler/src/dotty/tools/dotc/typer/ReTyper.scala

Lines changed: 22 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,7 @@ import core._
55
import Contexts._
66
import Types._
77
import Symbols._
8+
import StdNames._
89
import Decorators._
910
import typer.ProtoTypes._
1011
import ast.{tpd, untpd}
@@ -24,18 +25,20 @@ import config.Printers.typr
2425
class ReTyper extends Typer {
2526
import tpd._
2627

28+
private def assertTyped(tree: untpd.Tree)(implicit ctx: Context): Unit =
29+
assert(tree.hasType, i"$tree ${tree.getClass} ${tree.uniqueId}")
30+
2731
/** Checks that the given tree has been typed */
2832
protected def promote(tree: untpd.Tree)(implicit ctx: Context): tree.ThisTree[Type] = {
29-
assert(tree.hasType, i"$tree ${tree.getClass} ${tree.uniqueId}")
33+
assertTyped(tree)
3034
tree.withType(tree.typeOpt)
3135
}
3236

3337
override def typedIdent(tree: untpd.Ident, pt: Type)(implicit ctx: Context): Tree =
3438
promote(tree)
3539

3640
override def typedSelect(tree: untpd.Select, pt: Type)(implicit ctx: Context): Tree = {
37-
assert(tree.hasType, tree)
38-
// a qualifier cannot be a pattern
41+
assertTyped(tree)
3942
val qual1 = typed(tree.qualifier, AnySelectionProto)(ctx.retractMode(Mode.Pattern))
4043
untpd.cpy.Select(tree)(qual1, tree.name).withType(tree.typeOpt)
4144
}
@@ -49,11 +52,22 @@ class ReTyper extends Typer {
4952
override def typedSuper(tree: untpd.Super, pt: Type)(implicit ctx: Context): Tree =
5053
promote(tree)
5154

55+
override def typedTyped(tree: untpd.Typed, pt: Type)(implicit ctx: Context): Tree = {
56+
assertTyped(tree)
57+
val tpt1 = checkSimpleKinded(typedType(tree.tpt))
58+
val expr1 = tree.expr match {
59+
case id: untpd.Ident if (ctx.mode is Mode.Pattern) && untpd.isVarPattern(id) && (id.name == nme.WILDCARD || id.name == nme.WILDCARD_STAR) =>
60+
tree.expr.withType(tpt1.tpe)
61+
case _ => typed(tree.expr)
62+
}
63+
untpd.cpy.Typed(tree)(expr1, tpt1).withType(tree.typeOpt)
64+
}
65+
5266
override def typedTypeTree(tree: untpd.TypeTree, pt: Type)(implicit ctx: Context): TypeTree =
5367
promote(tree)
5468

5569
override def typedBind(tree: untpd.Bind, pt: Type)(implicit ctx: Context): Bind = {
56-
assert(tree.hasType)
70+
assertTyped(tree)
5771
val body1 = typed(tree.body, pt)
5872
untpd.cpy.Bind(tree)(tree.name, body1).withType(tree.typeOpt)
5973
}
@@ -65,6 +79,10 @@ class ReTyper extends Typer {
6579
untpd.cpy.UnApply(tree)(fun1, implicits1, patterns1).withType(tree.tpe)
6680
}
6781

82+
override def typedUnApply(tree: untpd.Apply, selType: Type)(implicit ctx: Context): Tree = {
83+
typedApply(tree, selType)
84+
}
85+
6886
override def localDummy(cls: ClassSymbol, impl: untpd.Template)(implicit ctx: Context) = impl.symbol
6987

7088
override def retrieveSym(tree: untpd.Tree)(implicit ctx: Context): Symbol = tree.symbol

compiler/src/dotty/tools/dotc/typer/TypeAssigner.scala

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -265,7 +265,6 @@ trait TypeAssigner {
265265
* - typed child trees it needs to access to cpmpute that type,
266266
* - any further information it needs to access to compute that type.
267267
*/
268-
269268
def assignType(tree: untpd.Ident, tp: Type)(implicit ctx: Context) =
270269
tree.withType(tp)
271270

compiler/src/dotty/tools/dotc/typer/Typer.scala

Lines changed: 2 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -664,8 +664,7 @@ class Typer extends Namer
664664

665665
def typedBlock(tree: untpd.Block, pt: Type)(implicit ctx: Context) = track("typedBlock") {
666666
val (exprCtx, stats1) = typedBlockStats(tree.stats)
667-
val ept = pt.notApplied
668-
val expr1 = typedExpr(tree.expr, ept)(exprCtx)
667+
val expr1 = typedExpr(tree.expr, pt.notApplied)(exprCtx)
669668
ensureNoLocalRefs(
670669
cpy.Block(tree)(stats1, expr1).withType(expr1.tpe), pt, localSyms(stats1))
671670
}
@@ -996,9 +995,7 @@ class Typer extends Namer
996995
cases mapconserve (typedCase(_, pt, selType, gadtSyms))
997996
}
998997

999-
/** Type a case. Overridden in ReTyper, that's why it's separate from
1000-
* typedCases.
1001-
*/
998+
/** Type a case. */
1002999
def typedCase(tree: untpd.CaseDef, pt: Type, selType: Type, gadtSyms: Set[Symbol])(implicit ctx: Context): CaseDef = track("typedCase") {
10031000
val originalCtx = ctx
10041001

tests/pos/inline-i1773.scala

Lines changed: 14 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,14 @@
1+
object Test {
2+
implicit class Foo(sc: StringContext) {
3+
object q {
4+
inline def unapply(arg: Any): Option[(Any, Any)] =
5+
Some((sc.parts(0), sc.parts(1)))
6+
}
7+
}
8+
9+
def main(args: Array[String]): Unit = {
10+
val q"class $name extends $parent" = new Object
11+
println(name)
12+
println(parent)
13+
}
14+
}

tests/pos/inline-i2570.scala

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,4 @@
1+
object Test {
2+
inline def sum2(ys: List[Int]): Int = (1 /: ys)(_ + _)
3+
val h1: ((List[Int]) => Int) = sum2
4+
}

tests/pos/inline-named-typeargs.scala

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,5 @@
1+
object t1 {
2+
inline def construct[Elem, Coll[_]](xs: List[Elem]): Coll[Elem] = ???
3+
4+
val xs3 = construct[Coll = List](List(1, 2, 3))
5+
}

tests/pos/inline-t2425.scala

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,8 @@
1+
object Test extends App {
2+
inline def foo[T](bar: T) = {
3+
bar match {
4+
case _ => ()
5+
}
6+
}
7+
foo(Array(1, 2))
8+
}

tests/pos/inline-t9232a.scala

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,11 @@
1+
final class Foo(val value: Int)
2+
3+
object Foo {
4+
inline def unapply(foo: Foo): Some[Int] = Some(foo.value)
5+
}
6+
7+
object Test {
8+
def transformTree(f: Foo): Any = f match {
9+
case Foo(_) => ???
10+
}
11+
}

tests/pos/inline-t9232b.scala

Lines changed: 23 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,23 @@
1+
final class Foo(val value: Int)
2+
3+
object Foo {
4+
inline def unapplySeq(foo: Foo): Some[Seq[Int]] = Some(List(foo.value))
5+
}
6+
7+
sealed trait Tree
8+
case class Node1(foo: Foo) extends Tree
9+
case class Node2() extends Tree
10+
11+
object Test {
12+
def transformTree(tree: Tree): Any = tree match {
13+
case Node1(Foo(_: _*)) => ???
14+
}
15+
16+
def transformTree2(tree: Tree): Any = tree match {
17+
case Node1(Foo(1, _: _*)) => ???
18+
}
19+
20+
def transformTree3(tree: Tree): Any = tree match {
21+
case Node1(Foo(x, _: _*)) => ???
22+
}
23+
}

0 commit comments

Comments
 (0)