Skip to content

Commit af3e5b0

Browse files
authored
Merge branch 'master' into dotty-scopt
2 parents e6cfaf6 + 086d1a8 commit af3e5b0

File tree

16 files changed

+149
-24
lines changed

16 files changed

+149
-24
lines changed

.gitmodules

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -187,3 +187,7 @@
187187
[submodule "community-build/community-projects/scopt"]
188188
path = community-build/community-projects/scopt
189189
url = https://github.com/scopt/scopt.git
190+
[submodule "community-build/community-projects/protoquill"]
191+
path = community-build/community-projects/protoquill
192+
url = https://github.com/dotty-staging/protoquill.git
193+
Submodule protoquill added at 5246493

community-build/src/scala/dotty/communitybuild/projects.scala

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -606,6 +606,14 @@ object projects:
606606
dependencies = List(scalatest, scalatestplusJunit, scalatestplusScalacheck)
607607
)
608608

609+
lazy val protoquill = SbtCommunityProject(
610+
project = "protoquill",
611+
sbtTestCommand = "test",
612+
sbtPublishCommand = "publishLocal",
613+
dependencies = List(), // TODO add scalatest and pprint (see protoquill/build.sbt)
614+
scalacOptions = List("-language:implicitConversions"), // disabled -Ycheck-init, due to bug in macro
615+
)
616+
609617
end projects
610618

611619
def allProjects = List(
@@ -672,6 +680,7 @@ def allProjects = List(
672680
projects.izumiReflect,
673681
projects.perspective,
674682
projects.akka,
683+
projects.protoquill,
675684
)
676685

677686
lazy val projectMap = allProjects.groupBy(_.project)

community-build/test/scala/dotty/communitybuild/CommunityBuildTest.scala

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -110,6 +110,7 @@ class CommunityBuildTestA extends CommunityBuildTest:
110110
@Test def upickle = projects.upickle.run()
111111
@Test def utest = projects.utest.run()
112112
@Test def zio = projects.zio.run()
113+
@Test def protoquill = projects.protoquill.run()
113114

114115
// 'scala-stm' and 'Sciss/Lucre':
115116
// @Test def scissEqual = projects.scissEqual .run()

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

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -825,8 +825,8 @@ object tpd extends Trees.Instance[Type] with TypedTreeInfo {
825825
val ownerAcc = new TreeAccumulator[immutable.Set[Symbol]] {
826826
def apply(ss: immutable.Set[Symbol], tree: Tree)(using Context) = tree match {
827827
case tree: DefTree =>
828-
if (tree.symbol.exists) ss + tree.symbol.owner
829-
else ss
828+
val sym = tree.symbol
829+
if sym.exists && !sym.owner.is(Package) then ss + sym.owner else ss
830830
case _ =>
831831
foldOver(ss, tree)
832832
}

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

Lines changed: 12 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -750,13 +750,23 @@ trait Applications extends Compatibility {
750750
}
751751
private def sameSeq[T <: Trees.Tree[?]](xs: List[T], ys: List[T]): Boolean = firstDiff(xs, ys) < 0
752752

753+
/** An argument is safe if it is a pure expression or a default getter call
754+
* If all arguments are safe, no reordering is necessary
755+
*/
756+
def isSafeArg(arg: Tree) =
757+
isPureExpr(arg)
758+
|| arg.isInstanceOf[RefTree | Apply | TypeApply] && arg.symbol.name.is(DefaultGetterName)
759+
753760
val result: Tree = {
754761
var typedArgs = typedArgBuf.toList
755762
def app0 = cpy.Apply(app)(normalizedFun, typedArgs) // needs to be a `def` because typedArgs can change later
756763
val app1 =
757764
if (!success) app0.withType(UnspecifiedErrorType)
758765
else {
759-
if (!sameSeq(args, orderedArgs.dropWhile(_ eq EmptyTree)) && !isJavaAnnotConstr(methRef.symbol)) {
766+
if !sameSeq(args, orderedArgs)
767+
&& !isJavaAnnotConstr(methRef.symbol)
768+
&& !typedArgs.forall(isSafeArg)
769+
then
760770
// need to lift arguments to maintain evaluation order in the
761771
// presence of argument reorderings.
762772

@@ -787,7 +797,7 @@ trait Applications extends Compatibility {
787797
argDefBuf.zip(impureArgIndices), (arg, idx) => originalIndex(idx)).map(_._1)
788798
}
789799
liftedDefs ++= orderedArgDefs
790-
}
800+
end if
791801
if (sameSeq(typedArgs, args)) // trick to cut down on tree copying
792802
typedArgs = args.asInstanceOf[List[Tree]]
793803
assignType(app0, normalizedFun, typedArgs)

compiler/src/scala/quoted/runtime/impl/QuotesImpl.scala

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -459,11 +459,11 @@ class QuotesImpl private (using val ctx: Context) extends Quotes, QuoteUnpickler
459459
val denot = qualifier.tpe.member(name.toTermName)
460460
assert(!denot.isOverloaded, s"The symbol `$name` is overloaded. The method Select.unique can only be used for non-overloaded symbols.")
461461
withDefaultPos(tpd.Select(qualifier, name.toTermName))
462-
def overloaded(qualifier: Term, name: String, targs: List[TypeRepr], args: List[Term]): Apply =
463-
withDefaultPos(tpd.applyOverloaded(qualifier, name.toTermName, args, targs, Types.WildcardType).asInstanceOf[Apply])
462+
def overloaded(qualifier: Term, name: String, targs: List[TypeRepr], args: List[Term]): Term =
463+
withDefaultPos(tpd.applyOverloaded(qualifier, name.toTermName, args, targs, Types.WildcardType))
464464

465-
def overloaded(qualifier: Term, name: String, targs: List[TypeRepr], args: List[Term], returnType: TypeRepr): Apply =
466-
withDefaultPos(tpd.applyOverloaded(qualifier, name.toTermName, args, targs, returnType).asInstanceOf[Apply])
465+
def overloaded(qualifier: Term, name: String, targs: List[TypeRepr], args: List[Term], returnType: TypeRepr): Term =
466+
withDefaultPos(tpd.applyOverloaded(qualifier, name.toTermName, args, targs, returnType))
467467
def copy(original: Tree)(qualifier: Term, name: String): Select =
468468
tpd.cpy.Select(original)(qualifier, name.toTermName)
469469
def unapply(x: Select): (Term, String) =

compiler/test/dotc/pos-test-pickling.blacklist

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -60,3 +60,6 @@ i9793.scala
6060

6161
# lazy_implicit symbol has different position after pickling
6262
i8182.scala
63+
64+
# local lifted value in annotation argument has different position after pickling
65+
i2797a

library/src/scala/quoted/Quotes.scala

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -783,10 +783,10 @@ trait Quotes { self: runtime.QuoteUnpickler & runtime.QuoteMatching =>
783783
def unique(qualifier: Term, name: String): Select
784784

785785
/** Call an overloaded method with the given type and term parameters */
786-
def overloaded(qualifier: Term, name: String, targs: List[TypeRepr], args: List[Term]): Apply
786+
def overloaded(qualifier: Term, name: String, targs: List[TypeRepr], args: List[Term]): Term
787787

788788
/** Call an overloaded method with the given type and term parameters */
789-
def overloaded(qualifier: Term, name: String, targs: List[TypeRepr], args: List[Term], returnType: TypeRepr): Apply
789+
def overloaded(qualifier: Term, name: String, targs: List[TypeRepr], args: List[Term], returnType: TypeRepr): Term
790790

791791
def copy(original: Tree)(qualifier: Term, name: String): Select
792792

Lines changed: 63 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,63 @@
1+
import scala.compiletime.{erasedValue, summonFrom}
2+
import scala.deriving._
3+
import scala.quoted._
4+
5+
trait Lft[T]:
6+
def toExpr(x: T)(using Type[T], Quotes): Expr[T] // TODO remove `Type[T]`
7+
8+
object Lft {
9+
given Lft[Int] with
10+
def toExpr(x: Int)(using Type[Int], Quotes) = Expr(x)
11+
12+
inline given derived[T](using inline m: Mirror.Of[T]): Lft[T] = ${ derivedExpr('m) }
13+
14+
private def derivedExpr[T](mirrorExpr: Expr[Mirror.Of[T]])(using qctx: Quotes, tpe: Type[T]): Expr[Lft[T]] = {
15+
mirrorExpr match {
16+
case '{ $mirrorExpr : Mirror.Sum { type MirroredElemTypes = mirroredElemTypes } } =>
17+
val liftables = Expr.ofSeq(elemTypesLfts[mirroredElemTypes])
18+
'{ new LiftableSum[T, mirroredElemTypes]($mirrorExpr, $liftables) }
19+
case '{ $mirrorExpr : Mirror.Product { type MirroredElemTypes = mirroredElemTypes } } =>
20+
val liftableExprs = Expr.ofSeq(elemTypesLfts[mirroredElemTypes])
21+
'{ new LiftableProduct[T, mirroredElemTypes]($mirrorExpr, $liftableExprs) }
22+
}
23+
}
24+
25+
class LiftableSum[T, MElemTypes](
26+
mirror: Mirror.Sum { type MirroredElemTypes = MElemTypes; type MirroredMonoType = T },
27+
liftables: Seq[Lft[_]] // TODO make Lft creation lazy
28+
) extends Lft[T]:
29+
def toExpr(x: T)(using Type[T], Quotes): Expr[T] =
30+
val ordinal = mirror.ordinal(x)
31+
val tp = Expr.summon[Mirror.SumOf[T]].get match
32+
case '{ $mirrorExpr : Mirror.Sum { type MirroredElemTypes = mirroredElemTypes } } =>
33+
elemType[mirroredElemTypes](ordinal)
34+
val liftable = liftables.apply(ordinal).asInstanceOf[Lft[T]]
35+
liftable.toExpr(x)(using tp.asInstanceOf[Type[T]], summon[Quotes])
36+
end LiftableSum
37+
38+
class LiftableProduct[T, MElemTypes](
39+
mirror: Mirror.Product { type MirroredElemTypes = MElemTypes; type MirroredMonoType = T },
40+
liftables: Seq[Lft[_]]
41+
) extends Lft[T]:
42+
def toExpr(x: T)(using Type[T], Quotes): Expr[T] =
43+
val mirrorExpr = Expr.summon[Mirror.ProductOf[T]].get
44+
val elemExprs =
45+
x.asInstanceOf[Product].productIterator.zip(liftables.iterator).map { (elem, lift) =>
46+
lift.asInstanceOf[Lft[Any]].toExpr(elem)
47+
}.toSeq
48+
val elemsTupleExpr = Expr.ofTupleFromSeq(elemExprs)
49+
'{ $mirrorExpr.fromProduct($elemsTupleExpr) }
50+
end LiftableProduct
51+
52+
private def elemTypesLfts[X: Type](using Quotes): List[Expr[Lft[_]]] =
53+
Type.of[X] match
54+
case '[ head *: tail ] =>
55+
Expr.summon[Lft[head]].getOrElse(quotes.reflect.report.throwError(s"Could not find given Lft[${Type.show[head]}]")) :: elemTypesLfts[tail]
56+
case '[ EmptyTuple ] => Nil
57+
58+
private def elemType[X: Type](ordinal: Int)(using Quotes): Type[_] =
59+
Type.of[X] match
60+
case '[ head *: tail ] =>
61+
if ordinal == 0 then Type.of[head]
62+
else elemType[tail](ordinal - 1)
63+
}
Lines changed: 24 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,24 @@
1+
2+
sealed trait Opt[+T] derives Lft
3+
case class Sm[T](t: T) extends Opt[T] derives Lft
4+
case object Nn extends Opt[Nothing] derives Lft
5+
6+
object Lib {
7+
8+
import scala.quoted._
9+
import Opt.*
10+
11+
inline def optTwo = ${optTwoExpr}
12+
inline def smTwo = ${smTwoExpr}
13+
inline def none = ${noneExpr}
14+
15+
private def optTwoExpr(using Quotes): Expr[Opt[Int]] =
16+
summon[Lft[Opt[Int]]].toExpr(Sm(2))
17+
18+
private def smTwoExpr(using Quotes): Expr[Sm[Int]] =
19+
summon[Lft[Sm[Int]]].toExpr(Sm(2))
20+
21+
private def noneExpr(using Quotes): Expr[Opt[Int]] =
22+
summon[Lft[Nn.type]].toExpr(Nn)
23+
}
24+
Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,6 @@
1+
object Test extends App {
2+
import Opt._
3+
assert(Lib.optTwo == Sm(2))
4+
assert(Lib.smTwo == Sm(2))
5+
assert(Lib.none == Nn)
6+
}

tests/run/i11571.check

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,2 @@
1+
17
2+
42

tests/run/i11571.scala

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,8 @@
1+
import util.chaining.scalaUtilChainingOps
2+
object Test extends App {
3+
def x = 42.tap(println(_))
4+
def y = 27.tap(println(_))
5+
def z = 17.tap(println(_))
6+
def f(i: Int = x, j: Int = y) = i + j
7+
f(j = z)
8+
}

tests/semanticdb/expect/NamedApplyBlock.expect.scala

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -3,12 +3,12 @@ package example
33
object NamedApplyBlockMethods/*<-example::NamedApplyBlockMethods.*/ {
44
val local/*<-example::NamedApplyBlockMethods.local.*/ = 1
55
def foo/*<-example::NamedApplyBlockMethods.foo().*/(a/*<-example::NamedApplyBlockMethods.foo().(a)*/: Int/*->scala::Int#*/ = 1, b/*<-example::NamedApplyBlockMethods.foo().(b)*/: Int/*->scala::Int#*/ = 2, c/*<-example::NamedApplyBlockMethods.foo().(c)*/: Int/*->scala::Int#*/ = 3): Int/*->scala::Int#*/ = a/*->example::NamedApplyBlockMethods.foo().(a)*/ +/*->scala::Int#`+`(+4).*/ b/*->example::NamedApplyBlockMethods.foo().(b)*/ +/*->scala::Int#`+`(+4).*/ c/*->example::NamedApplyBlockMethods.foo().(c)*/
6-
def baseCase/*<-example::NamedApplyBlockMethods.baseCase().*/ = foo/*->example::NamedApplyBlockMethods.foo().*//*->local0*/(local/*->example::NamedApplyBlockMethods.local.*/, c/*->example::NamedApplyBlockMethods.foo().(c)*/ = 3)
7-
def recursive/*<-example::NamedApplyBlockMethods.recursive().*/ = foo/*->example::NamedApplyBlockMethods.foo().*//*->local2*/(local/*->example::NamedApplyBlockMethods.local.*/, c/*->example::NamedApplyBlockMethods.foo().(c)*/ = foo/*->example::NamedApplyBlockMethods.foo().*//*->local3*/(local/*->example::NamedApplyBlockMethods.local.*/, c/*->example::NamedApplyBlockMethods.foo().(c)*/ = 3))
6+
def baseCase/*<-example::NamedApplyBlockMethods.baseCase().*/ = foo/*->example::NamedApplyBlockMethods.foo().*/(local/*->example::NamedApplyBlockMethods.local.*/, c/*->example::NamedApplyBlockMethods.foo().(c)*/ = 3)
7+
def recursive/*<-example::NamedApplyBlockMethods.recursive().*/ = foo/*->example::NamedApplyBlockMethods.foo().*//*->local1*/(local/*->example::NamedApplyBlockMethods.local.*/, c/*->example::NamedApplyBlockMethods.foo().(c)*/ = foo/*->example::NamedApplyBlockMethods.foo().*/(local/*->example::NamedApplyBlockMethods.local.*/, c/*->example::NamedApplyBlockMethods.foo().(c)*/ = 3))
88
}
99

1010
object NamedApplyBlockCaseClassConstruction/*<-example::NamedApplyBlockCaseClassConstruction.*/ {
1111
case class Msg/*<-example::NamedApplyBlockCaseClassConstruction.Msg#*/(body/*<-example::NamedApplyBlockCaseClassConstruction.Msg#body.*/: String/*->scala::Predef.String#*/, head/*<-example::NamedApplyBlockCaseClassConstruction.Msg#head.*/: String/*->scala::Predef.String#*/ = "default", tail/*<-example::NamedApplyBlockCaseClassConstruction.Msg#tail.*/: String/*->scala::Predef.String#*/)
1212
val bodyText/*<-example::NamedApplyBlockCaseClassConstruction.bodyText.*/ = "body"
13-
val msg/*<-example::NamedApplyBlockCaseClassConstruction.msg.*/ = Msg/*->example::NamedApplyBlockCaseClassConstruction.Msg.*//*->local4*//*->example::NamedApplyBlockCaseClassConstruction.Msg.apply().*/(bodyText/*->example::NamedApplyBlockCaseClassConstruction.bodyText.*/, tail/*->example::NamedApplyBlockCaseClassConstruction.Msg.apply().(tail)*/ = "tail")
13+
val msg/*<-example::NamedApplyBlockCaseClassConstruction.msg.*/ = Msg/*->example::NamedApplyBlockCaseClassConstruction.Msg.*//*->example::NamedApplyBlockCaseClassConstruction.Msg.apply().*/(bodyText/*->example::NamedApplyBlockCaseClassConstruction.bodyText.*/, tail/*->example::NamedApplyBlockCaseClassConstruction.Msg.apply().(tail)*/ = "tail")
1414
}

tests/semanticdb/metac.expect

Lines changed: 5 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -2157,8 +2157,8 @@ Schema => SemanticDB v4
21572157
Uri => NamedApplyBlock.scala
21582158
Text => empty
21592159
Language => Scala
2160-
Symbols => 46 entries
2161-
Occurrences => 46 entries
2160+
Symbols => 43 entries
2161+
Occurrences => 43 entries
21622162

21632163
Symbols:
21642164
example/NamedApplyBlockCaseClassConstruction. => final object NamedApplyBlockCaseClassConstruction
@@ -2202,11 +2202,8 @@ example/NamedApplyBlockMethods.foo().(b) => param b
22022202
example/NamedApplyBlockMethods.foo().(c) => param c
22032203
example/NamedApplyBlockMethods.local. => val method local
22042204
example/NamedApplyBlockMethods.recursive(). => method recursive
2205-
local0 => val local b$1
2206-
local1 => val local c$1
2207-
local2 => val local b$3
2208-
local3 => val local b$2
2209-
local4 => val local head$1
2205+
local0 => val local c$1
2206+
local1 => val local b$1
22102207

22112208
Occurrences:
22122209
[0:8..0:15): example <- example/
@@ -2227,16 +2224,14 @@ Occurrences:
22272224
[4:61..4:62): c -> example/NamedApplyBlockMethods.foo().(c)
22282225
[5:6..5:14): baseCase <- example/NamedApplyBlockMethods.baseCase().
22292226
[5:17..5:20): foo -> example/NamedApplyBlockMethods.foo().
2230-
[5:17..5:17): -> local0
22312227
[5:21..5:26): local -> example/NamedApplyBlockMethods.local.
22322228
[5:28..5:29): c -> example/NamedApplyBlockMethods.foo().(c)
22332229
[6:6..6:15): recursive <- example/NamedApplyBlockMethods.recursive().
22342230
[6:18..6:21): foo -> example/NamedApplyBlockMethods.foo().
2235-
[6:18..6:18): -> local2
2231+
[6:18..6:18): -> local1
22362232
[6:22..6:27): local -> example/NamedApplyBlockMethods.local.
22372233
[6:29..6:30): c -> example/NamedApplyBlockMethods.foo().(c)
22382234
[6:33..6:36): foo -> example/NamedApplyBlockMethods.foo().
2239-
[6:33..6:33): -> local3
22402235
[6:37..6:42): local -> example/NamedApplyBlockMethods.local.
22412236
[6:44..6:45): c -> example/NamedApplyBlockMethods.foo().(c)
22422237
[9:7..9:43): NamedApplyBlockCaseClassConstruction <- example/NamedApplyBlockCaseClassConstruction.
@@ -2251,7 +2246,6 @@ Occurrences:
22512246
[11:6..11:14): bodyText <- example/NamedApplyBlockCaseClassConstruction.bodyText.
22522247
[12:6..12:9): msg <- example/NamedApplyBlockCaseClassConstruction.msg.
22532248
[12:12..12:15): Msg -> example/NamedApplyBlockCaseClassConstruction.Msg.
2254-
[12:12..12:12): -> local4
22552249
[12:15..12:15): -> example/NamedApplyBlockCaseClassConstruction.Msg.apply().
22562250
[12:16..12:24): bodyText -> example/NamedApplyBlockCaseClassConstruction.bodyText.
22572251
[12:26..12:30): tail -> example/NamedApplyBlockCaseClassConstruction.Msg.apply().(tail)

0 commit comments

Comments
 (0)