Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Support for Scala 3 #18

Merged
merged 12 commits into from
Mar 6, 2022
4 changes: 4 additions & 0 deletions .github/workflows/actions.yml
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,10 @@ name: ci

on:
push:
branches:
- master
tags:
- '*'
pull_request:
branches:
- master
Expand Down
56 changes: 33 additions & 23 deletions build.sc
Original file line number Diff line number Diff line change
@@ -1,21 +1,26 @@
import mill._, scalalib._, scalajslib._, scalanativelib._, publish._
import mill.scalalib.api.Util.isScala3
import scalalib._
import $ivy.`de.tototec::de.tobiasroeser.mill.vcs.version_mill0.9:0.1.1`
import $ivy.`de.tototec::de.tobiasroeser.mill.vcs.version::0.1.4`
import de.tobiasroeser.mill.vcs.version.VcsVersion
import $ivy.`com.github.lolgab::mill-mima_mill0.9:0.0.4`
import $ivy.`com.github.lolgab::mill-mima::0.0.9`
import com.github.lolgab.mill.mima._

val scala212 = "2.12.13"
val scala213 = "2.13.4"
val scala30 = "3.0.2"
val scala31 = "3.1.1"

val scala2Versions = List(scala212, scala213)

val scalaJSVersions = for {
scalaV <- Seq(scala213, scala212)
scalaJSV <- Seq("1.4.0")
scalaV <- scala30 :: scala2Versions
scalaJSV <- Seq("1.5.1")
} yield (scalaV, scalaJSV)

val scalaNativeVersions = for {
scalaV <- Seq(scala213, scala212)
scalaNativeV <- Seq("0.4.0")
scalaV <- scala2Versions
scalaNativeV <- Seq("0.4.3")
} yield (scalaV, scalaNativeV)

trait MainArgsPublishModule extends PublishModule with CrossScalaModule with Mima {
Expand All @@ -26,6 +31,8 @@ trait MainArgsPublishModule extends PublishModule with CrossScalaModule with Mim
.lastTag
.getOrElse(throw new Exception("Missing last tag"))
)
// Remove after Scala 3 artifacts are published
def mimaPreviousArtifacts = T{ if(isScala3(scalaVersion())) Seq() else super.mimaPreviousArtifacts() }
def artifactName = "mainargs"

def pomSettings = PomSettings(
Expand All @@ -39,54 +46,57 @@ trait MainArgsPublishModule extends PublishModule with CrossScalaModule with Mim
)
)

def scalacOptions = super.scalacOptions() ++ Seq("-P:acyclic:force")
def scalacOptions = super.scalacOptions() ++ (if (!isScala3(crossScalaVersion)) Seq("-P:acyclic:force") else Seq.empty)

def scalacPluginIvyDeps = super.scalacPluginIvyDeps() ++ Agg(ivy"com.lihaoyi::acyclic:0.2.0")
def scalacPluginIvyDeps = super.scalacPluginIvyDeps() ++ (if (!isScala3(crossScalaVersion)) Agg(ivy"com.lihaoyi::acyclic:0.2.0") else Agg.empty)

def compileIvyDeps = super.compileIvyDeps() ++ Agg(
ivy"com.lihaoyi::acyclic:0.2.0",
ivy"org.scala-lang:scala-reflect:$crossScalaVersion"
)
def compileIvyDeps = super.compileIvyDeps() ++ (if (!isScala3(crossScalaVersion)) Agg(
ivy"com.lihaoyi::acyclic:0.2.0",
ivy"org.scala-lang:scala-reflect:$crossScalaVersion"
) else Agg.empty)

def ivyDeps = Agg(
ivy"org.scala-lang.modules::scala-collection-compat::2.4.0"
)
ivy"org.scala-lang.modules::scala-collection-compat::2.4.4"
) ++ Agg(ivy"com.lihaoyi::pprint:0.6.6")
}

def scalaMajor(scalaVersion: String) = if(isScala3(scalaVersion)) "3" else "2"

trait Common extends CrossScalaModule {
def millSourcePath = build.millSourcePath / "mainargs"
def sources = T.sources(
millSourcePath / "src",
millSourcePath / s"src-$platform"
millSourcePath / s"src-$platform",
millSourcePath / s"src-${scalaMajor(scalaVersion())}",
)
def platform: String
}

trait CommonTestModule extends ScalaModule with TestModule {
def ivyDeps = Agg(ivy"com.lihaoyi::utest::0.7.6")
def testFrameworks = Seq("utest.runner.Framework")
trait CommonTestModule extends ScalaModule with TestModule.Utest {
def ivyDeps = Agg(ivy"com.lihaoyi::utest::0.7.11")
def sources = T.sources(
millSourcePath / "src",
millSourcePath / s"src-$platform"
millSourcePath / s"src-$platform",
millSourcePath / s"src-${scalaMajor(scalaVersion())}",
)
def platform: String
}


object mainargs extends Module {
object jvm extends Cross[JvmMainArgsModule](scala212, scala213)
object jvm extends Cross[JvmMainArgsModule](scala30 :: scala2Versions: _*)
class JvmMainArgsModule(val crossScalaVersion: String)
extends Common with ScalaModule with MainArgsPublishModule {
def platform = "jvm"
object test extends Tests with CommonTestModule{
def platform = "jvm"
def ivyDeps = super.ivyDeps() ++ Agg(ivy"com.lihaoyi::os-lib:0.7.1")
def ivyDeps = super.ivyDeps() ++ Agg(ivy"com.lihaoyi::os-lib:0.7.8")
}
}

object js extends Cross[JSMainArgsModule](scalaJSVersions: _*)
class JSMainArgsModule(val crossScalaVersion: String, crossJSVersion: String)
extends Common with ScalaJSModule with MainArgsPublishModule {
extends Common with MainArgsPublishModule with ScalaJSModule {
def platform = "js"
def scalaJSVersion = crossJSVersion
object test extends Tests with CommonTestModule{
Expand All @@ -96,7 +106,7 @@ object mainargs extends Module {

object native extends Cross[NativeMainArgsModule](scalaNativeVersions: _*)
class NativeMainArgsModule(val crossScalaVersion: String, crossScalaNativeVersion: String)
extends Common with ScalaNativeModule with MainArgsPublishModule {
extends Common with MainArgsPublishModule with ScalaNativeModule {
def scalaNativeVersion = crossScalaNativeVersion
def platform = "native"
object test extends Tests with CommonTestModule{
Expand Down
File renamed without changes.
9 changes: 9 additions & 0 deletions mainargs/src-2/ParserForClassCompanionVersionSpecific.scala
Original file line number Diff line number Diff line change
@@ -0,0 +1,9 @@
package mainargs

import acyclic.skipped

import scala.language.experimental.macros

private[mainargs] trait ParserForClassCompanionVersionSpecific {
def apply[T]: ParserForClass[T] = macro Macros.parserForClass[T]
}
9 changes: 9 additions & 0 deletions mainargs/src-2/ParserForMethodsCompanionVersionSpecific.scala
Original file line number Diff line number Diff line change
@@ -0,0 +1,9 @@
package mainargs

import acyclic.skipped

import scala.language.experimental.macros

private[mainargs] trait ParserForMethodsCompanionVersionSpecific {
def apply[B](base: B): ParserForMethods[B] = macro Macros.parserForMethods[B]
}
155 changes: 155 additions & 0 deletions mainargs/src-3/Macros.scala
Original file line number Diff line number Diff line change
@@ -0,0 +1,155 @@
package mainargs

import scala.quoted._

object Macros {
lolgab marked this conversation as resolved.
Show resolved Hide resolved
private def mainAnnotation(using Quotes) = quotes.reflect.TypeRepr.of[mainargs.main].typeSymbol
private def argAnnotation(using Quotes) = quotes.reflect.TypeRepr.of[mainargs.arg].typeSymbol

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This should be a bit more performant

  private def argAnnotation(using Quotes) = quotes.reflect.TypeRepr.typeConstructorOf[mainargs.arg].typeSymbol

Or maybe this one is even better

  private def argAnnotation(using Quotes) = quotes.reflect.Symbol.requiredClass("mainargs.arg")

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Same for mainAnnotation

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Done, thank you ✅

def parserForMethods[B](base: Expr[B])(using Quotes, Type[B]): Expr[ParserForMethods[B]] = {
import quotes.reflect._
val allMethods = TypeRepr.of[B].typeSymbol.memberMethods
val annotatedMethodsWithMainAnnotations = allMethods.flatMap { methodSymbol =>
methodSymbol.getAnnotation(mainAnnotation).map(methodSymbol -> _)
}.sortBy(_._1.pos.map(_.start))
val mainDatas = Expr.ofList(annotatedMethodsWithMainAnnotations.map { (annotatedMethod, mainAnnotationInstance) =>
createMainData[Any, B](annotatedMethod, mainAnnotationInstance)
})

'{
new ParserForMethods[B](
MethodMains[B](${ mainDatas }, () => ${ base })

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
MethodMains[B](${ mainDatas }, () => ${ base })
MethodMains[B]($mainDatas, () => $base)

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Done, thank you ✅

)
}
}

def parserForClass[B](using Quotes, Type[B]): Expr[ParserForClass[B]] = {
import quotes.reflect._
val typeReprOfB = TypeRepr.of[B]
val companionModule = typeReprOfB match {

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Is there a chance that B doesn't have a companion module?
If so then a graceful fail might be needed here (or if typeSymbolOfB is NoSymbol)

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

If so then a graceful fail might be needed here (or if typeSymbolOfB is NoSymbol)

Do you know how? typeSymbolOfB is not undefined. But the compiler crashes in a way I cannot understand 🤔


#2] [info] exception occurred while compiling /Users/lorenzo/scala/mainargs/mainargs/test/src-3/VersionSpecific.scala, /Users/lorenzo/scala/mainargs/mainargs/test/src/Checker.scala, /Users/lorenzo/scala/mainargs/mainargs/test/src/ClassTests.scala, /Users/lorenzo/scala/mainargs/mainargs/test/src/CoreTests.scala, /Users/lorenzo/scala/mainargs/mainargs/test/src/DashedArgumentName.scala, /Users/lorenzo/scala/mainargs/mainargs/test/src/FlagTests.scala, /Users/lorenzo/scala/mainargs/mainargs/test/src/HelloWorldTests.scala, /Users/lorenzo/scala/mainargs/mainargs/test/src/HygieneTests.scala, /Users/lorenzo/scala/mainargs/mainargs/test/src/MacroTests.scala, /Users/lorenzo/scala/mainargs/mainargs/test/src/ManyTests.scala, /Users/lorenzo/scala/mainargs/mainargs/test/src/NewVarargsTests.scala, /Users/lorenzo/scala/mainargs/mainargs/test/src/OptionSeqTests.scala, /Users/lorenzo/scala/mainargs/mainargs/test/src/ParserTests.scala, /Users/lorenzo/scala/mainargs/mainargs/test/src/PositionalTests.scala, /Users/lorenzo/scala/mainargs/mainargs/test/src/TestUtils.scala, /Users/lorenzo/scala/mainargs/mainargs/test/src/VarargsTests.scala
[#0] scala.MatchError: Ident(apply) (of class dotty.tools.dotc.ast.Trees$Ident) while compiling /Users/lorenzo/scala/mainargs/mainargs/test/src-3/VersionSpecific.scala, /Users/lorenzo/scala/mainargs/mainargs/test/src/Checker.scala, /Users/lorenzo/scala/mainargs/mainargs/test/src/ClassTests.scala, /Users/lorenzo/scala/mainargs/mainargs/test/src/CoreTests.scala, /Users/lorenzo/scala/mainargs/mainargs/test/src/DashedArgumentName.scala, /Users/lorenzo/scala/mainargs/mainargs/test/src/FlagTests.scala, /Users/lorenzo/scala/mainargs/mainargs/test/src/HelloWorldTests.scala, /Users/lorenzo/scala/mainargs/mainargs/test/src/HygieneTests.scala, /Users/lorenzo/scala/mainargs/mainargs/test/src/MacroTests.scala, /Users/lorenzo/scala/mainargs/mainargs/test/src/ManyTests.scala, /Users/lorenzo/scala/mainargs/mainargs/test/src/NewVarargsTests.scala, /Users/lorenzo/scala/mainargs/mainargs/test/src/OptionSeqTests.scala, /Users/lorenzo/scala/mainargs/mainargs/test/src/ParserTests.scala, /Users/lorenzo/scala/mainargs/mainargs/test/src/PositionalTests.scala, /Users/lorenzo/scala/mainargs/mainargs/test/src/TestUtils.scala, /Users/lorenzo/scala/mainargs/mainargs/test/src/VarargsTests.scala
[#2] [error] ## Exception when compiling 16 sources to /Users/lorenzo/scala/mainargs/out/mainargs/jvm/3.0.2/test/compile.dest/classes
[#2] [error] scala.MatchError: Ident(apply) (of class dotty.tools.dotc.ast.Trees$Ident)
[#2] [error] dotty.tools.dotc.typer.Typer.newExpr$1(Typer.scala:3759)
[#2] [error] dotty.tools.dotc.typer.Typer.adapt1(Typer.scala:3804)
[#2] [error] dotty.tools.dotc.typer.Typer.adapt(Typer.scala:3162)
[#2] [error] dotty.tools.dotc.typer.Typer.typed(Typer.scala:2821)
[#2] [error] dotty.tools.dotc.typer.Typer.typed(Typer.scala:2825)
[#2] [error] dotty.tools.dotc.typer.Typer.typedExpr(Typer.scala:2941)
[#2] [error] dotty.tools.dotc.typer.Applications.realApply$1(Applications.scala:882)
[#2] [error] dotty.tools.dotc.typer.Applications.typedApply(Applications.scala:1032)
[#2] [error] dotty.tools.dotc.typer.Applications.typedApply$(Applications.scala:317)
[#2] [error] dotty.tools.dotc.typer.Inliner$InlineTyper.typedApply(Inliner.scala:1535)
[#2] [error] dotty.tools.dotc.typer.Typer.typedUnnamed$1(Typer.scala:2693)
[#2] [error] dotty.tools.dotc.typer.Typer.typedUnadapted(Typer.scala:2756)
[#2] [error] dotty.tools.dotc.typer.ReTyper.typedUnadapted(ReTyper.scala:118)
[#2] [error] dotty.tools.dotc.typer.Inliner$InlineTyper.typedUnadapted(Inliner.scala:1622)
[#2] [error] dotty.tools.dotc.typer.Typer.typed(Typer.scala:2821)
[#2] [error] dotty.tools.dotc.typer.Typer.typed(Typer.scala:2818)
[#2] [error] dotty.tools.dotc.typer.Typer.typed(Typer.scala:2825)
[#2] [error] dotty.tools.dotc.typer.Typer.typedInlined(Typer.scala:1768)
[#2] [error] dotty.tools.dotc.typer.Typer.typedUnnamed$1(Typer.scala:2715)
[#2] [error] dotty.tools.dotc.typer.Typer.typedUnadapted(Typer.scala:2756)
[#2] [error] dotty.tools.dotc.typer.ReTyper.typedUnadapted(ReTyper.scala:118)
[#2] [error] dotty.tools.dotc.typer.Inliner$InlineTyper.typedUnadapted(Inliner.scala:1622)
[#2] [error] dotty.tools.dotc.typer.Typer.typed(Typer.scala:2821)
[#2] [error] dotty.tools.dotc.typer.Typer.typed(Typer.scala:2825)
[#2] [error] dotty.tools.dotc.typer.Typer.typedExpr(Typer.scala:2941)
[#2] [error] dotty.tools.dotc.typer.Typer.$anonfun$34(Typer.scala:2156)
[#2] [error] dotty.tools.dotc.typer.PrepareInlineable$.dropInlineIfError(PrepareInlineable.scala:225)
[#2] [error] dotty.tools.dotc.typer.Typer.typedDefDef(Typer.scala:2156)
[#2] [error] dotty.tools.dotc.typer.Typer.typedNamed$1(Typer.scala:2670)
[#2] [error] dotty.tools.dotc.typer.Typer.typedUnadapted(Typer.scala:2755)
[#2] [error] dotty.tools.dotc.typer.ReTyper.typedUnadapted(ReTyper.scala:118)
[#2] [error] dotty.tools.dotc.typer.Inliner$InlineTyper.typedUnadapted(Inliner.scala:1622)
[#2] [error] dotty.tools.dotc.typer.Typer.typed(Typer.scala:2821)
[#2] [error] dotty.tools.dotc.typer.Typer.typed(Typer.scala:2825)
[#2] [error] dotty.tools.dotc.typer.Typer.traverse$1(Typer.scala:2847)
[#2] [error] dotty.tools.dotc.typer.Typer.typedStats(Typer.scala:2897)
[#2] [error] dotty.tools.dotc.typer.Typer.typedBlockStats(Typer.scala:1025)
[#2] [error] dotty.tools.dotc.typer.Typer.typedBlock(Typer.scala:1029)
[#2] [error] dotty.tools.dotc.typer.Typer.typedUnnamed$1(Typer.scala:2701)
[#2] [error] dotty.tools.dotc.typer.Typer.typedUnadapted(Typer.scala:2756)
[#2] [error] dotty.tools.dotc.typer.ReTyper.typedUnadapted(ReTyper.scala:118)
[#2] [error] dotty.tools.dotc.typer.Inliner$InlineTyper.typedUnadapted(Inliner.scala:1622)
[#2] [error] dotty.tools.dotc.typer.Typer.typed(Typer.scala:2821)
[#2] [error] dotty.tools.dotc.typer.Typer.typed(Typer.scala:2825)
[#2] [error] dotty.tools.dotc.typer.Inliner$InlineTyper.typedSelect(Inliner.scala:1492)
[#2] [error] dotty.tools.dotc.typer.Typer.typedNamed$1(Typer.scala:2663)
[#2] [error] dotty.tools.dotc.typer.Typer.typedUnadapted(Typer.scala:2755)
[#2] [error] dotty.tools.dotc.typer.ReTyper.typedUnadapted(ReTyper.scala:118)
[#2] [error] dotty.tools.dotc.typer.Inliner$InlineTyper.typedUnadapted(Inliner.scala:1622)
[#2] [error] dotty.tools.dotc.typer.Typer.typed(Typer.scala:2821)
[#2] [error] dotty.tools.dotc.typer.Typer.typed(Typer.scala:2825)
[#2] [error] dotty.tools.dotc.typer.Typer.typedExpr(Typer.scala:2941)
[#2] [error] dotty.tools.dotc.typer.Applications.typedTypeApply(Applications.scala:1084)
[#2] [error] dotty.tools.dotc.typer.Applications.typedTypeApply$(Applications.scala:317)
[#2] [error] dotty.tools.dotc.typer.Inliner$InlineTyper.typedTypeApply(Inliner.scala:1549)
[#2] [error] dotty.tools.dotc.typer.Typer.typedUnnamed$1(Typer.scala:2712)
[#2] [error] dotty.tools.dotc.typer.Typer.typedUnadapted(Typer.scala:2756)
[#2] [error] dotty.tools.dotc.typer.ReTyper.typedUnadapted(ReTyper.scala:118)
[#2] [error] dotty.tools.dotc.typer.Inliner$InlineTyper.typedUnadapted(Inliner.scala:1622)
[#2] [error] dotty.tools.dotc.typer.Typer.typed(Typer.scala:2821)
[#2] [error] dotty.tools.dotc.typer.Typer.typed(Typer.scala:2825)
[#2] [error] dotty.tools.dotc.typer.Typer.typedInlined(Typer.scala:1768)
[#2] [error] dotty.tools.dotc.typer.Typer.typedUnnamed$1(Typer.scala:2715)
[#2] [error] dotty.tools.dotc.typer.Typer.typedUnadapted(Typer.scala:2756)
[#2] [error] dotty.tools.dotc.typer.ReTyper.typedUnadapted(ReTyper.scala:118)
[#2] [error] dotty.tools.dotc.typer.Inliner$InlineTyper.typedUnadapted(Inliner.scala:1622)
[#2] [error] dotty.tools.dotc.typer.Typer.typed(Typer.scala:2821)
[#2] [error] dotty.tools.dotc.typer.Typer.typed(Typer.scala:2825)
[#2] [error] dotty.tools.dotc.typer.Typer.typedInlined(Typer.scala:1768)
[#2] [error] dotty.tools.dotc.typer.Typer.typedUnnamed$1(Typer.scala:2715)
[#2] [error] dotty.tools.dotc.typer.Typer.typedUnadapted(Typer.scala:2756)
[#2] [error] dotty.tools.dotc.typer.ReTyper.typedUnadapted(ReTyper.scala:118)
[#2] [error] dotty.tools.dotc.typer.Inliner$InlineTyper.typedUnadapted(Inliner.scala:1622)
[#2] [error] dotty.tools.dotc.typer.ProtoTypes$FunProto.$anonfun$5(ProtoTypes.scala:428)
[#2] [error] dotty.tools.dotc.typer.ProtoTypes$FunProto.cacheTypedArg(ProtoTypes.scala:359)
[#2] [error] dotty.tools.dotc.typer.ProtoTypes$FunProto.typedArg(ProtoTypes.scala:429)
[#2] [error] dotty.tools.dotc.typer.Applications$ApplyToUntyped.typedArg(Applications.scala:850)
[#2] [error] dotty.tools.dotc.typer.Applications$ApplyToUntyped.typedArg(Applications.scala:850)
[#2] [error] dotty.tools.dotc.typer.Applications$Application.addTyped$1(Applications.scala:544)
[#2] [error] dotty.tools.dotc.typer.Applications$Application.matchArgs(Applications.scala:609)
[#2] [error] dotty.tools.dotc.typer.Applications$Application.matchArgs(Applications.scala:609)
[#2] [error] dotty.tools.dotc.typer.Applications$Application.matchArgs(Applications.scala:609)
[#2] [error] dotty.tools.dotc.typer.Applications$Application.matchArgs(Applications.scala:609)
[#2] [error] dotty.tools.dotc.typer.Applications$Application.init(Applications.scala:447)
[#2] [error] dotty.tools.dotc.typer.Applications$TypedApply.<init>(Applications.scala:735)
[#2] [error] dotty.tools.dotc.typer.Applications$ApplyToUntyped.<init>(Applications.scala:849)
[#2] [error] dotty.tools.dotc.typer.Applications.ApplyTo(Applications.scala:1057)
[#2] [error] dotty.tools.dotc.typer.Applications.ApplyTo$(Applications.scala:317)
[#2] [error] dotty.tools.dotc.typer.Typer.ApplyTo(Typer.scala:106)
[#2] [error] dotty.tools.dotc.typer.Applications.simpleApply$1(Applications.scala:904)
[#2] [error] dotty.tools.dotc.typer.Applications.realApply$5$$anonfun$4(Applications.scala:983)
[#2] [error] dotty.tools.dotc.typer.Typer.tryEither(Typer.scala:2949)
[#2] [error] dotty.tools.dotc.typer.Applications.realApply$1(Applications.scala:994)
[#2] [error] dotty.tools.dotc.typer.Applications.typedApply(Applications.scala:1032)
[#2] [error] dotty.tools.dotc.typer.Applications.typedApply$(Applications.scala:317)
[#2] [error] dotty.tools.dotc.typer.Inliner$InlineTyper.typedApply(Inliner.scala:1535)
[#2] [error] dotty.tools.dotc.typer.Typer.typedUnnamed$1(Typer.scala:2693)
[#2] [error] dotty.tools.dotc.typer.Typer.typedUnadapted(Typer.scala:2756)
[#2] [error] dotty.tools.dotc.typer.ReTyper.typedUnadapted(ReTyper.scala:118)
[#2] [error] dotty.tools.dotc.typer.Inliner$InlineTyper.typedUnadapted(Inliner.scala:1622)
[#2] [error] dotty.tools.dotc.typer.Typer.typed(Typer.scala:2821)
[#2] [error] dotty.tools.dotc.typer.Typer.typed(Typer.scala:2825)
[#2] [error] dotty.tools.dotc.typer.Typer.typedInlined(Typer.scala:1768)
[#2] [error] dotty.tools.dotc.typer.Typer.typedUnnamed$1(Typer.scala:2715)
[#2] [error] dotty.tools.dotc.typer.Typer.typedUnadapted(Typer.scala:2756)
[#2] [error] dotty.tools.dotc.typer.ReTyper.typedUnadapted(ReTyper.scala:118)
[#2] [error] dotty.tools.dotc.typer.Inliner$InlineTyper.typedUnadapted(Inliner.scala:1622)
[#2] [error] dotty.tools.dotc.typer.Typer.typed(Typer.scala:2821)
[#2] [error] dotty.tools.dotc.typer.Typer.typed(Typer.scala:2825)
[#2] [error] dotty.tools.dotc.typer.Typer.typedInlined(Typer.scala:1768)
[#2] [error] dotty.tools.dotc.typer.Typer.typedUnnamed$1(Typer.scala:2715)
[#2] [error] dotty.tools.dotc.typer.Typer.typedUnadapted(Typer.scala:2756)
[#2] [error] dotty.tools.dotc.typer.ReTyper.typedUnadapted(ReTyper.scala:118)
[#2] [error] dotty.tools.dotc.typer.Inliner$InlineTyper.typedUnadapted(Inliner.scala:1622)
[#2] [error] dotty.tools.dotc.typer.Typer.typed(Typer.scala:2821)
[#2] [error] dotty.tools.dotc.typer.Typer.typed(Typer.scala:2825)
[#2] [error] dotty.tools.dotc.typer.Inliner$InlineTyper.typedSelect(Inliner.scala:1492)
[#2] [error] dotty.tools.dotc.typer.Typer.typedNamed$1(Typer.scala:2663)
[#2] [error] dotty.tools.dotc.typer.Typer.typedUnadapted(Typer.scala:2755)
[#2] [error] dotty.tools.dotc.typer.ReTyper.typedUnadapted(ReTyper.scala:118)
[#2] [error] dotty.tools.dotc.typer.Inliner$InlineTyper.typedUnadapted(Inliner.scala:1622)
[#2] [error] dotty.tools.dotc.typer.Typer.typed(Typer.scala:2821)
[#2] [error] dotty.tools.dotc.typer.Typer.typed(Typer.scala:2825)
[#2] [error] dotty.tools.dotc.typer.Typer.typedExpr(Typer.scala:2941)
[#2] [error] dotty.tools.dotc.typer.Applications.typedTypeApply(Applications.scala:1084)
[#2] [error] dotty.tools.dotc.typer.Applications.typedTypeApply$(Applications.scala:317)
[#2] [error] dotty.tools.dotc.typer.Inliner$InlineTyper.typedTypeApply(Inliner.scala:1549)
[#2] [error] dotty.tools.dotc.typer.Typer.typedUnnamed$1(Typer.scala:2712)
[#2] [error] dotty.tools.dotc.typer.Typer.typedUnadapted(Typer.scala:2756)
[#2] [error] dotty.tools.dotc.typer.ReTyper.typedUnadapted(ReTyper.scala:118)
[#2] [error] dotty.tools.dotc.typer.Inliner$InlineTyper.typedUnadapted(Inliner.scala:1622)
[#2] [error] dotty.tools.dotc.typer.ProtoTypes$FunProto.$anonfun$5(ProtoTypes.scala:428)
[#2] [error] dotty.tools.dotc.typer.ProtoTypes$FunProto.cacheTypedArg(ProtoTypes.scala:359)
[#2] [error] dotty.tools.dotc.typer.ProtoTypes$FunProto.typedArg(ProtoTypes.scala:429)
[#2] [error] dotty.tools.dotc.typer.Applications$ApplyToUntyped.typedArg(Applications.scala:850)
[#2] [error] dotty.tools.dotc.typer.Applications$ApplyToUntyped.typedArg(Applications.scala:850)
[#2] [error] dotty.tools.dotc.typer.Applications$Application.addTyped$1(Applications.scala:544)
[#2] [error] dotty.tools.dotc.typer.Applications$Application.matchArgs(Applications.scala:609)
[#2] [error] dotty.tools.dotc.typer.Applications$Application.init(Applications.scala:447)
[#2] [error] dotty.tools.dotc.typer.Applications$TypedApply.<init>(Applications.scala:735)
[#2] [error] dotty.tools.dotc.typer.Applications$ApplyToUntyped.<init>(Applications.scala:849)
[#2] [error] dotty.tools.dotc.typer.Applications.ApplyTo(Applications.scala:1057)
[#2] [error] dotty.tools.dotc.typer.Applications.ApplyTo$(Applications.scala:317)
[#2] [error] dotty.tools.dotc.typer.Typer.ApplyTo(Typer.scala:106)
[#2] [error] dotty.tools.dotc.typer.Applications.simpleApply$1(Applications.scala:904)
[#2] [error] dotty.tools.dotc.typer.Applications.realApply$5$$anonfun$4(Applications.scala:983)
[#2] [error] dotty.tools.dotc.typer.Typer.tryEither(Typer.scala:2949)
[#2] [error] dotty.tools.dotc.typer.Applications.realApply$1(Applications.scala:994)
[#2] [error] dotty.tools.dotc.typer.Applications.typedApply(Applications.scala:1032)
[#2] [error] dotty.tools.dotc.typer.Applications.typedApply$(Applications.scala:317)
[#2] [error] dotty.tools.dotc.typer.Inliner$InlineTyper.typedApply(Inliner.scala:1535)
[#2] [error] dotty.tools.dotc.typer.Typer.typedUnnamed$1(Typer.scala:2693)
[#2] [error] dotty.tools.dotc.typer.Typer.typedUnadapted(Typer.scala:2756)
[#2] [error] dotty.tools.dotc.typer.ReTyper.typedUnadapted(ReTyper.scala:118)
[#2] [error] dotty.tools.dotc.typer.Inliner$InlineTyper.typedUnadapted(Inliner.scala:1622)
[#2] [error] dotty.tools.dotc.typer.ProtoTypes$FunProto.$anonfun$5(ProtoTypes.scala:428)
[#2] [error] dotty.tools.dotc.typer.ProtoTypes$FunProto.cacheTypedArg(ProtoTypes.scala:359)
[#2] [error] dotty.tools.dotc.typer.ProtoTypes$FunProto.typedArg(ProtoTypes.scala:429)
[#2] [error] dotty.tools.dotc.typer.Applications$ApplyToUntyped.typedArg(Applications.scala:850)
[#2] [error] dotty.tools.dotc.typer.Applications$ApplyToUntyped.typedArg(Applications.scala:850)
[#2] [error] dotty.tools.dotc.typer.Applications$Application.addTyped$1(Applications.scala:544)
[#2] [error] dotty.tools.dotc.typer.Applications$Application.matchArgs(Applications.scala:609)
[#2] [error] dotty.tools.dotc.typer.Applications$Application.init(Applications.scala:447)
[#2] [error] dotty.tools.dotc.typer.Applications$TypedApply.<init>(Applications.scala:735)
[#2] [error] dotty.tools.dotc.typer.Applications$ApplyToUntyped.<init>(Applications.scala:849)
[#2] [error] dotty.tools.dotc.typer.Applications.ApplyTo(Applications.scala:1057)
[#2] [error] dotty.tools.dotc.typer.Applications.ApplyTo$(Applications.scala:317)
[#2] [error] dotty.tools.dotc.typer.Typer.ApplyTo(Typer.scala:106)
[#2] [error] dotty.tools.dotc.typer.Applications.simpleApply$1(Applications.scala:904)
[#2] [error] dotty.tools.dotc.typer.Applications.realApply$5$$anonfun$4(Applications.scala:983)
[#2] [error] dotty.tools.dotc.typer.Typer.tryEither(Typer.scala:2949)
[#2] [error] dotty.tools.dotc.typer.Applications.realApply$1(Applications.scala:994)
[#2] [error] dotty.tools.dotc.typer.Applications.typedApply(Applications.scala:1032)
[#2] [error] dotty.tools.dotc.typer.Applications.typedApply$(Applications.scala:317)
[#2] [error] dotty.tools.dotc.typer.Inliner$InlineTyper.typedApply(Inliner.scala:1535)
[#2] [error] dotty.tools.dotc.typer.Typer.typedUnnamed$1(Typer.scala:2693)
[#2] [error] dotty.tools.dotc.typer.Typer.typedUnadapted(Typer.scala:2756)
[#2] [error] dotty.tools.dotc.typer.ReTyper.typedUnadapted(ReTyper.scala:118)
[#2] [error] dotty.tools.dotc.typer.Inliner$InlineTyper.typedUnadapted(Inliner.scala:1622)
[#2] [error] dotty.tools.dotc.typer.Typer.typed(Typer.scala:2821)
[#2] [error] dotty.tools.dotc.typer.Typer.typed(Typer.scala:2825)
[#2] [error] dotty.tools.dotc.typer.Typer.typedInlined(Typer.scala:1768)
[#2] [error] dotty.tools.dotc.typer.Typer.typedUnnamed$1(Typer.scala:2715)
[#2] [error] dotty.tools.dotc.typer.Typer.typedUnadapted(Typer.scala:2756)
[#2] [error] dotty.tools.dotc.typer.ReTyper.typedUnadapted(ReTyper.scala:118)
[#2] [error] dotty.tools.dotc.typer.Inliner$InlineTyper.typedUnadapted(Inliner.scala:1622)
[#2] [error] dotty.tools.dotc.typer.Typer.typed(Typer.scala:2821)
[#2] [error] dotty.tools.dotc.typer.Typer.typed(Typer.scala:2818)
[#2] [error] dotty.tools.dotc.typer.Typer.typed(Typer.scala:2825)
[#2] [error] dotty.tools.dotc.typer.Typer.typedExpr(Typer.scala:2941)
[#2] [error] dotty.tools.dotc.typer.Inliner$InlineTyper.typedApply(Inliner.scala:1540)
[#2] [error] dotty.tools.dotc.typer.Typer.typedUnnamed$1(Typer.scala:2693)
[#2] [error] dotty.tools.dotc.typer.Typer.typedUnadapted(Typer.scala:2756)
[#2] [error] dotty.tools.dotc.typer.ReTyper.typedUnadapted(ReTyper.scala:118)
[#2] [error] dotty.tools.dotc.typer.Inliner$InlineTyper.typedUnadapted(Inliner.scala:1622)
[#2] [error] dotty.tools.dotc.typer.Typer.typed(Typer.scala:2821)
[#2] [error] dotty.tools.dotc.typer.Typer.typed(Typer.scala:2825)
[#2] [error] dotty.tools.dotc.typer.ReTyper.typedTyped(ReTyper.scala:62)
[#2] [error] dotty.tools.dotc.typer.Typer.typedUnnamed$1(Typer.scala:2698)
[#2] [error] dotty.tools.dotc.typer.Typer.typedUnadapted(Typer.scala:2756)
[#2] [error] dotty.tools.dotc.typer.ReTyper.typedUnadapted(ReTyper.scala:118)
[#2] [error] dotty.tools.dotc.typer.Inliner$InlineTyper.typedUnadapted(Inliner.scala:1622)
[#2] [error] dotty.tools.dotc.typer.Typer.typed(Typer.scala:2821)
[#2] [error] dotty.tools.dotc.typer.Typer.typed(Typer.scala:2818)
[#2] [error] dotty.tools.dotc.typer.Typer.typed(Typer.scala:2825)
[#2] [error] dotty.tools.dotc.typer.Inliner.inlined(Inliner.scala:1016)
[#2] [error] dotty.tools.dotc.typer.Inliner$.inlineCall(Inliner.scala:153)
[#2] [error] dotty.tools.dotc.transform.Inlining$InliningTreeMap.transform(Inlining.scala:86)
[#2] [error] dotty.tools.dotc.ast.Trees$Instance$TreeMap.transform(Trees.scala:1420)
[#2] [error] dotty.tools.dotc.ast.TreeMapWithImplicits.transform(TreeMapWithImplicits.scala:120)
[#2] [error] dotty.tools.dotc.transform.Inlining$InliningTreeMap.transform(Inlining.scala:94)
[#2] [error] dotty.tools.dotc.ast.Trees$Instance$TreeMap.transform$$anonfun$1(Trees.scala:1490)
[#2] [error] scala.collection.immutable.List.mapConserve(List.scala:472)
[#2] [error] dotty.tools.dotc.ast.Trees$Instance$TreeMap.transform(Trees.scala:1490)
[#2] [error] dotty.tools.dotc.ast.Trees$Instance$TreeMap.transform(Trees.scala:1386)
[#2] [error] dotty.tools.dotc.ast.TreeMapWithImplicits.transform(TreeMapWithImplicits.scala:120)
[#2] [error] dotty.tools.dotc.transform.Inlining$InliningTreeMap.transform(Inlining.scala:94)
[#2] [error] dotty.tools.dotc.ast.Trees$Instance$TreeMap.transform(Trees.scala:1420)
[#2] [error] dotty.tools.dotc.ast.TreeMapWithImplicits.transform(TreeMapWithImplicits.scala:120)
[#2] [error] dotty.tools.dotc.transform.Inlining$InliningTreeMap.transform(Inlining.scala:94)
[#2] [error] dotty.tools.dotc.ast.Trees$Instance$TreeMap.transform(Trees.scala:1420)
[#2] [error] dotty.tools.dotc.ast.TreeMapWithImplicits.transform(TreeMapWithImplicits.scala:120)
[#2] [error] dotty.tools.dotc.transform.Inlining$InliningTreeMap.transform(Inlining.scala:94)
[#2] [error] dotty.tools.dotc.ast.Trees$Instance$TreeMap.transform$$anonfun$1(Trees.scala:1490)
[#2] [error] scala.collection.immutable.List.mapConserve(List.scala:472)
[#2] [error] dotty.tools.dotc.ast.Trees$Instance$TreeMap.transform(Trees.scala:1490)
[#2] [error] dotty.tools.dotc.ast.Trees$Instance$TreeMap.transform(Trees.scala:1386)
[#2] [error] dotty.tools.dotc.ast.TreeMapWithImplicits.transform(TreeMapWithImplicits.scala:120)
[#2] [error] dotty.tools.dotc.transform.Inlining$InliningTreeMap.transform(Inlining.scala:94)
[#2] [error] dotty.tools.dotc.ast.Trees$Instance$TreeMap.transform(Trees.scala:1420)
[#2] [error] dotty.tools.dotc.ast.TreeMapWithImplicits.transform(TreeMapWithImplicits.scala:120)
[#2] [error] dotty.tools.dotc.transform.Inlining$InliningTreeMap.transform(Inlining.scala:94)
[#2] [error] dotty.tools.dotc.ast.Trees$Instance$TreeMap.transform$$anonfun$1(Trees.scala:1490)
[#2] [error] scala.collection.immutable.List.mapConserve(List.scala:472)
[#2] [error] dotty.tools.dotc.ast.Trees$Instance$TreeMap.transform(Trees.scala:1490)
[#2] [error] dotty.tools.dotc.ast.Trees$Instance$TreeMap.transform(Trees.scala:1418)
[#2] [error] dotty.tools.dotc.ast.TreeMapWithImplicits.transform(TreeMapWithImplicits.scala:120)
[#2] [error] dotty.tools.dotc.transform.Inlining$InliningTreeMap.transform(Inlining.scala:94)
[#2] [error] dotty.tools.dotc.ast.Trees$Instance$TreeMap.transform(Trees.scala:1420)
[#2] [error] dotty.tools.dotc.ast.TreeMapWithImplicits.transform(TreeMapWithImplicits.scala:120)
[#2] [error] dotty.tools.dotc.transform.Inlining$InliningTreeMap.transform(Inlining.scala:94)
[#2] [error] dotty.tools.dotc.ast.Trees$Instance$TreeMap.transform(Trees.scala:1394)
[#2] [error] dotty.tools.dotc.ast.TreeMapWithImplicits.transform(TreeMapWithImplicits.scala:120)
[#2] [error] dotty.tools.dotc.transform.Inlining$InliningTreeMap.transform(Inlining.scala:82)
[#2] [error] dotty.tools.dotc.ast.Trees$Instance$TreeMap.transform$$anonfun$1(Trees.scala:1490)
[#2] [error] scala.collection.immutable.List.mapConserve(List.scala:472)
[#2] [error] dotty.tools.dotc.ast.Trees$Instance$TreeMap.transform(Trees.scala:1490)
[#2] [error] dotty.tools.dotc.ast.Trees$Instance$TreeMap.transform(Trees.scala:1386)
[#2] [error] dotty.tools.dotc.ast.TreeMapWithImplicits.transform(TreeMapWithImplicits.scala:120)
[#2] [error] dotty.tools.dotc.transform.Inlining$InliningTreeMap.transform(Inlining.scala:94)
[#2] [error] dotty.tools.dotc.ast.Trees$Instance$TreeMap.transform(Trees.scala:1420)
[#2] [error] dotty.tools.dotc.ast.TreeMapWithImplicits.transform(TreeMapWithImplicits.scala:120)
[#2] [error] dotty.tools.dotc.transform.Inlining$InliningTreeMap.transform(Inlining.scala:94)
[#2] [error] dotty.tools.dotc.ast.Trees$Instance$TreeMap.transform(Trees.scala:1420)
[#2] [error] dotty.tools.dotc.ast.TreeMapWithImplicits.transform(TreeMapWithImplicits.scala:120)
[#2] [error] dotty.tools.dotc.transform.Inlining$InliningTreeMap.transform(Inlining.scala:94)
[#2] [error] dotty.tools.dotc.ast.Trees$Instance$TreeMap.transform(Trees.scala:1380)
[#2] [error] dotty.tools.dotc.ast.TreeMapWithImplicits.transform(TreeMapWithImplicits.scala:120)
[#2] [error] dotty.tools.dotc.transform.Inlining$InliningTreeMap.transform(Inlining.scala:94)
[#2] [error] dotty.tools.dotc.ast.Trees$Instance$TreeMap.transform$$anonfun$1(Trees.scala:1490)
[#2] [error] scala.collection.immutable.List.mapConserve(List.scala:472)
[#2] [error] dotty.tools.dotc.ast.Trees$Instance$TreeMap.transform(Trees.scala:1490)
[#2] [error] dotty.tools.dotc.ast.Trees$Instance$TreeMap.transform(Trees.scala:1386)
[#2] [error] dotty.tools.dotc.ast.TreeMapWithImplicits.transform(TreeMapWithImplicits.scala:120)
[#2] [error] dotty.tools.dotc.transform.Inlining$InliningTreeMap.transform(Inlining.scala:94)
[#2] [error] dotty.tools.dotc.ast.Trees$Instance$TreeMap.transform(Trees.scala:1420)
[#2] [error] dotty.tools.dotc.ast.TreeMapWithImplicits.transform(TreeMapWithImplicits.scala:120)
[#2] [error] dotty.tools.dotc.transform.Inlining$InliningTreeMap.transform(Inlining.scala:94)
[#2] [error] dotty.tools.dotc.ast.Trees$Instance$TreeMap.transform(Trees.scala:1420)
[#2] [error] dotty.tools.dotc.ast.TreeMapWithImplicits.transform(TreeMapWithImplicits.scala:120)
[#2] [error] dotty.tools.dotc.transform.Inlining$InliningTreeMap.transform(Inlining.scala:94)
[#2] [error] dotty.tools.dotc.ast.Trees$Instance$TreeMap.transform$$anonfun$1(Trees.scala:1490)
[#2] [error] scala.collection.immutable.List.mapConserve(List.scala:472)
[#2] [error] dotty.tools.dotc.ast.Trees$Instance$TreeMap.transform(Trees.scala:1490)
[#2] [error] dotty.tools.dotc.ast.Trees$Instance$TreeMap.transform(Trees.scala:1386)
[#2] [error] dotty.tools.dotc.ast.TreeMapWithImplicits.transform(TreeMapWithImplicits.scala:120)
[#2] [error] dotty.tools.dotc.transform.Inlining$InliningTreeMap.transform(Inlining.scala:94)
[#2] [error] dotty.tools.dotc.ast.Trees$Instance$TreeMap.transform(Trees.scala:1420)
[#2] [error] dotty.tools.dotc.ast.TreeMapWithImplicits.transform(TreeMapWithImplicits.scala:120)
[#2] [error] dotty.tools.dotc.transform.Inlining$InliningTreeMap.transform(Inlining.scala:94)
[#2] [error] dotty.tools.dotc.ast.Trees$Instance$TreeMap.transform(Trees.scala:1420)
[#2] [error] dotty.tools.dotc.ast.TreeMapWithImplicits.transform(TreeMapWithImplicits.scala:120)
[#2] [error] dotty.tools.dotc.transform.Inlining$InliningTreeMap.transform(Inlining.scala:94)
[#2] [error] dotty.tools.dotc.ast.Trees$Instance$TreeMap.transform$$anonfun$1(Trees.scala:1490)
[#2] [error] scala.collection.immutable.List.mapConserve(List.scala:472)
[#2] [error] dotty.tools.dotc.ast.Trees$Instance$TreeMap.transform(Trees.scala:1490)
[#2] [error] dotty.tools.dotc.ast.Trees$Instance$TreeMap.transform(Trees.scala:1386)
[#2] [error] dotty.tools.dotc.ast.TreeMapWithImplicits.transform(TreeMapWithImplicits.scala:120)
[#2] [error] dotty.tools.dotc.transform.Inlining$InliningTreeMap.transform(Inlining.scala:94)
[#2] [error] dotty.tools.dotc.ast.Trees$Instance$TreeMap.transform(Trees.scala:1420)
[#2] [error] dotty.tools.dotc.ast.TreeMapWithImplicits.transform(TreeMapWithImplicits.scala:120)
[#2] [error] dotty.tools.dotc.transform.Inlining$InliningTreeMap.transform(Inlining.scala:94)
[#2] [error] dotty.tools.dotc.ast.Trees$Instance$TreeMap.transform(Trees.scala:1420)
[#2] [error] dotty.tools.dotc.ast.TreeMapWithImplicits.transform(TreeMapWithImplicits.scala:120)
[#2] [error] dotty.tools.dotc.transform.Inlining$InliningTreeMap.transform(Inlining.scala:94)
[#2] [error] dotty.tools.dotc.ast.Trees$Instance$TreeMap.transform(Trees.scala:1454)
[#2] [error] dotty.tools.dotc.ast.TreeMapWithImplicits.transform(TreeMapWithImplicits.scala:120)
[#2] [error] dotty.tools.dotc.transform.Inlining$InliningTreeMap.transform(Inlining.scala:80)
[#2] [error] dotty.tools.dotc.ast.TreeMapWithImplicits.traverse$1(TreeMapWithImplicits.scala:53)
[#2] [error] dotty.tools.dotc.ast.TreeMapWithImplicits.transformStats(TreeMapWithImplicits.scala:60)
[#2] [error] dotty.tools.dotc.ast.TreeMapWithImplicits.transform(TreeMapWithImplicits.scala:111)
[#2] [error] dotty.tools.dotc.transform.Inlining$InliningTreeMap.transform(Inlining.scala:80)
[#2] [error] dotty.tools.dotc.ast.Trees$Instance$TreeMap.transform(Trees.scala:1463)
[#2] [error] dotty.tools.dotc.ast.TreeMapWithImplicits.transform(TreeMapWithImplicits.scala:120)
[#2] [error] dotty.tools.dotc.transform.Inlining$InliningTreeMap.transform(Inlining.scala:80)
[#2] [error] dotty.tools.dotc.ast.TreeMapWithImplicits.traverse$1(TreeMapWithImplicits.scala:53)
[#2] [error] dotty.tools.dotc.ast.TreeMapWithImplicits.transformStats(TreeMapWithImplicits.scala:60)
[#2] [error] dotty.tools.dotc.ast.Trees$Instance$TreeMap.transform(Trees.scala:1474)
[#2] [error] dotty.tools.dotc.ast.TreeMapWithImplicits.transform(TreeMapWithImplicits.scala:120)
[#2] [error] dotty.tools.dotc.transform.Inlining$InliningTreeMap.transform(Inlining.scala:94)
[#2] [error] dotty.tools.dotc.transform.Inlining$$anon$2.transform(Inlining.scala:72)
[#2] [error] dotty.tools.dotc.transform.MacroTransform.run(MacroTransform.scala:21)
[#2] [error] dotty.tools.dotc.transform.Inlining.run(Inlining.scala:44)
[#2] [error] dotty.tools.dotc.core.Phases$Phase.runOn$$anonfun$1(Phases.scala:303)
[#2] [error] scala.collection.immutable.List.map(List.scala:250)
[#2] [error] dotty.tools.dotc.core.Phases$Phase.runOn(Phases.scala:304)
[#2] [error] dotty.tools.dotc.transform.Inlining.runOn(Inlining.scala:48)
[#2] [error] dotty.tools.dotc.Run.runPhases$4$$anonfun$4(Run.scala:205)
[#2] [error] scala.runtime.function.JProcedure1.apply(JProcedure1.java:15)
[#2] [error] scala.runtime.function.JProcedure1.apply(JProcedure1.java:10)
[#2] [error] scala.collection.ArrayOps$.foreach$extension(ArrayOps.scala:1323)
[#2] [error] dotty.tools.dotc.Run.runPhases$5(Run.scala:216)
[#2] [error] dotty.tools.dotc.Run.compileUnits$$anonfun$1(Run.scala:224)
[#2] [error] scala.runtime.java8.JFunction0$mcV$sp.apply(JFunction0$mcV$sp.scala:18)
[#2] [error] dotty.tools.dotc.util.Stats$.maybeMonitored(Stats.scala:67)
[#2] [error] dotty.tools.dotc.Run.compileUnits(Run.scala:231)
[#2] [error] dotty.tools.dotc.Run.compileSources(Run.scala:166)
[#2] [error] dotty.tools.dotc.Run.compile(Run.scala:150)
[#2] [error] dotty.tools.dotc.Driver.doCompile(Driver.scala:39)
[#2] [error] dotty.tools.xsbt.CompilerBridgeDriver.run(CompilerBridgeDriver.java:88)
[#2] [error] dotty.tools.xsbt.CompilerBridge.run(CompilerBridge.java:22)
[#2] [error] sbt.internal.inc.AnalyzingCompiler.compile(AnalyzingCompiler.scala:91)
[#2] [error] sbt.internal.inc.MixedAnalyzingCompiler.$anonfun$compile$7(MixedAnalyzingCompiler.scala:192)
[#2] [error] scala.runtime.java8.JFunction0$mcV$sp.apply(JFunction0$mcV$sp.scala:18)
[#2] [error] sbt.internal.inc.MixedAnalyzingCompiler.timed(MixedAnalyzingCompiler.scala:247)
[#2] [error] sbt.internal.inc.MixedAnalyzingCompiler.$anonfun$compile$4(MixedAnalyzingCompiler.scala:182)
[#2] [error] sbt.internal.inc.MixedAnalyzingCompiler.$anonfun$compile$4$adapted(MixedAnalyzingCompiler.scala:163)
[#2] [error] sbt.internal.inc.JarUtils$.withPreviousJar(JarUtils.scala:239)
[#2] [error] sbt.internal.inc.MixedAnalyzingCompiler.compileScala$1(MixedAnalyzingCompiler.scala:163)
[#2] [error] sbt.internal.inc.MixedAnalyzingCompiler.compile(MixedAnalyzingCompiler.scala:210)
[#2] [error] sbt.internal.inc.IncrementalCompilerImpl.$anonfun$compileInternal$1(IncrementalCompilerImpl.scala:528)
[#2] [error] sbt.internal.inc.IncrementalCompilerImpl.$anonfun$compileInternal$1$adapted(IncrementalCompilerImpl.scala:528)
[#2] [error] sbt.internal.inc.Incremental$.$anonfun$apply$5(Incremental.scala:177)
[#2] [error] sbt.internal.inc.Incremental$.$anonfun$apply$5$adapted(Incremental.scala:175)
[#2] [error] sbt.internal.inc.Incremental$$anon$2.run(Incremental.scala:461)
[#2] [error] sbt.internal.inc.IncrementalCommon$CycleState.next(IncrementalCommon.scala:116)
[#2] [error] sbt.internal.inc.IncrementalCommon$$anon$1.next(IncrementalCommon.scala:56)
[#2] [error] sbt.internal.inc.IncrementalCommon$$anon$1.next(IncrementalCommon.scala:52)
[#2] [error] sbt.internal.inc.IncrementalCommon.cycle(IncrementalCommon.scala:263)
[#2] [error] sbt.internal.inc.Incremental$.$anonfun$incrementalCompile$8(Incremental.scala:416)
[#2] [error] sbt.internal.inc.Incremental$.withClassfileManager(Incremental.scala:503)
[#2] [error] sbt.internal.inc.Incremental$.incrementalCompile(Incremental.scala:403)
[#2] [error] sbt.internal.inc.Incremental$.apply(Incremental.scala:169)
[#2] [error] sbt.internal.inc.IncrementalCompilerImpl.compileInternal(IncrementalCompilerImpl.scala:528)
[#2] [error] sbt.internal.inc.IncrementalCompilerImpl.$anonfun$compileIncrementally$1(IncrementalCompilerImpl.scala:482)
[#2] [error] sbt.internal.inc.IncrementalCompilerImpl.handleCompilationError(IncrementalCompilerImpl.scala:332)
[#2] [error] sbt.internal.inc.IncrementalCompilerImpl.compileIncrementally(IncrementalCompilerImpl.scala:420)
[#2] [error] sbt.internal.inc.IncrementalCompilerImpl.compile(IncrementalCompilerImpl.scala:137)
[#2] [error] mill.scalalib.worker.ZincWorkerImpl.compileInternal(ZincWorkerImpl.scala:544)
[#2] [error] mill.scalalib.worker.ZincWorkerImpl.$anonfun$compileMixed0$1(ZincWorkerImpl.scala:317)
[#2] [error] mill.api.FixSizedCache.withCachedValue(FixSizedCache.scala:66)
[#2] [error] mill.scalalib.worker.ZincWorkerImpl.withCompilers(ZincWorkerImpl.scala:399)
[#2] [error] mill.scalalib.worker.ZincWorkerImpl.compileMixed0(ZincWorkerImpl.scala:316)
[#2] [error] mill.scalalib.worker.ZincWorkerImpl.compileMixed(ZincWorkerImpl.scala:284)
[#2] [error] mill.scalalib.ScalaModule.$anonfun$compile$2(ScalaModule.scala:195)
[#2] [error] mill.define.Task$TraverseCtx.evaluate(Task.scala:376)
[#2] [error] mill.eval.Evaluator.$anonfun$evaluateGroup$13(Evaluator.scala:505)
[#2] [error] scala.util.DynamicVariable.withValue(DynamicVariable.scala:59)
[#2] [error] scala.Console$.withErr(Console.scala:193)
[#2] [error] mill.eval.Evaluator.$anonfun$evaluateGroup$12(Evaluator.scala:505)
[#2] [error] scala.util.DynamicVariable.withValue(DynamicVariable.scala:59)
[#2] [error] scala.Console$.withOut(Console.scala:164)
[#2] [error] mill.eval.Evaluator.$anonfun$evaluateGroup$11(Evaluator.scala:504)
[#2] [error] scala.util.DynamicVariable.withValue(DynamicVariable.scala:59)
[#2] [error] scala.Console$.withIn(Console.scala:227)
[#2] [error] mill.eval.Evaluator.$anonfun$evaluateGroup$8(Evaluator.scala:503)
[#2] [error] mill.eval.Evaluator.$anonfun$evaluateGroup$8$adapted(Evaluator.scala:464)
[#2] [error] scala.collection.immutable.Vector.foreach(Vector.scala:1856)
[#2] [error] mill.eval.Evaluator.evaluateGroup(Evaluator.scala:464)
[#2] [error] mill.eval.Evaluator.$anonfun$evaluateGroupCached$13(Evaluator.scala:359)
[#2] [error] scala.util.DynamicVariable.withValue(DynamicVariable.scala:59)
[#2] [error] mill.eval.Evaluator.evaluateGroupCached(Evaluator.scala:350)
[#2] [error] mill.eval.Evaluator.$anonfun$parallelEvaluate$2(Evaluator.scala:227)
[#2] [error] scala.concurrent.impl.Promise$Transformation.run(Promise.scala:467)
[#2] [error] java.util.concurrent.Executors$RunnableAdapter.call(Executors.java:511)
[#2] [error] java.util.concurrent.FutureTask.run(FutureTask.java:266)
[#2] [error] java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1149)
[#2] [error] java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:624)
[#2] [error] java.lang.Thread.run(Thread.java:748)

case TypeRef(a,b) => TermRef(a,b)
}
val typeSymbolOfB = typeReprOfB.typeSymbol
val companionModuleType = typeSymbolOfB.companionModule.tree.asInstanceOf[ValDef].tpt.tpe.asType
val companionModuleExpr = Ident(companionModule).asExpr
val mainAnnotationInstance = typeSymbolOfB.getAnnotation(mainAnnotation).getOrElse {
report.error(
lolgab marked this conversation as resolved.
Show resolved Hide resolved
s"cannot find @main annotation on ${companionModule.name}",
typeSymbolOfB.pos.get
)
???
}
val annotatedMethod = TypeRepr.of[B].typeSymbol.companionModule.memberMethod("apply").head
companionModuleType match
case '[bCompanion] =>
val mainData = createMainData[B, bCompanion](annotatedMethod, mainAnnotationInstance)
lolgab marked this conversation as resolved.
Show resolved Hide resolved
'{
new ParserForClass[B](
ClassMains[B](${ mainData }.asInstanceOf[MainData[B, Any]], () => ${ Ident(companionModule).asExpr })
)
}
}

def createMainData[T: Type, B: Type](using Quotes)(method: quotes.reflect.Symbol, annotation: quotes.reflect.Term): Expr[MainData[T, B]] = {
import quotes.reflect.*
val params = method.paramSymss.headOption.getOrElse(throw new Exception("Multiple parameter lists not supported"))
lolgab marked this conversation as resolved.
Show resolved Hide resolved
val defaultParams = getDefaultParams(method)
val argSigs = Expr.ofList(params.map { param =>
val paramTree = param.tree.asInstanceOf[ValDef]
val paramTpe = paramTree.tpt.tpe
val arg = param.getAnnotation(argAnnotation).map(_.asExpr.asInstanceOf[Expr[mainargs.arg]]).getOrElse('{ new mainargs.arg() })
lolgab marked this conversation as resolved.
Show resolved Hide resolved
val paramType = paramTpe.asType
paramType match
case '[t] =>
val defaultParam: Expr[Option[B => t]] = defaultParams.get(param) match {
case Some(v) => '{ Some(((_: B) => $v).asInstanceOf[B => t]) }

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I wonder if you can do something like this and avoid the asInstanceOf

            case Some('{ $p: `t`}) => '{ Some(((_: B) => $v)) }

`t` reverse to the outer t and does not create a new type variable in the pattern

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Done, thank you ✅

case None => '{ None }
}
val argReader = Expr.summon[mainargs.ArgReader[t]].getOrElse{
report.error(
lolgab marked this conversation as resolved.
Show resolved Hide resolved
s"No mainargs.ArgReader of ###companionModule### found for parameter ${param.name}",
param.pos.get
)
'{ ??? }
}
'{ (ArgSig.create[t, B](${ Expr(param.name) }, ${ arg }, ${ defaultParam })(using ${ argReader })).asInstanceOf[ArgSig[Any, B]] }

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

You might be able to avoid the cast if you do ArgSig.create[Any, B](...)

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Otherwise I would sugest using asExprOf

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I tried both without success.

})

val invokeRaw: Expr[(B, Seq[Any]) => T] = {
def callOf(args: Expr[Seq[Any]]) = call(method, '{ Seq( ${ args }) })
'{ ((b: B, params: Seq[Any]) => ${ callOf('{ params }) }).asInstanceOf[(B, Seq[Any]) => T] }

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Try using asExprOf on the quote instead of asInstanceOf inside of it.

Copy link
Member Author

@lolgab lolgab Mar 4, 2022

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Done ✅

}
'{ MainData.create[T, B](${ Expr(method.name) }, ${ annotation.asExprOf[mainargs.main] }, ${ argSigs }, ${ invokeRaw }) }
}

/** Call a method given by its symbol.
*
* E.g.
*
* assuming:
*
* def foo(x: Int, y: String)(z: Int)
*
* val argss: List[List[Any]] = ???
*
* then:
*
* call(<symbol of foo>, '{argss})
*
* will expand to:
*
* foo(argss(0)(0), argss(0)(1))(argss(1)(0))
*
*/
private def call(using Quotes)(
method: quotes.reflect.Symbol,
argss: Expr[Seq[Seq[Any]]]
): Expr[_] = {
// Copy pasted from Cask.
// https://github.com/com-lihaoyi/cask/blob/65b9c8e4fd528feb71575f6e5ef7b5e2e16abbd9/cask/src-3/cask/router/Macros.scala#L106
import quotes.reflect._
val paramss = method.paramSymss

if (paramss.isEmpty) {
report.error("At least one parameter list must be declared.", method.pos.get)
lolgab marked this conversation as resolved.
Show resolved Hide resolved
return '{???}
}

val fct = Ref(method)

val accesses: List[List[Term]] = for (i <- paramss.indices.toList) yield {
for (j <- paramss(i).indices.toList) yield {
val tpe = paramss(i)(j).tree.asInstanceOf[ValDef].tpt.tpe
tpe.asType match
case '[t] => '{ $argss(${Expr(i)})(${Expr(j)}).asInstanceOf[t] }.asTerm
}
}

val base = Apply(fct, accesses.head)
val application: Apply = accesses.tail.foldLeft(base)((lhs, args) => Apply(lhs, args))
val expr = application.asExpr
expr
}


/** Lookup default values for a method's parameters. */
private def getDefaultParams(using Quotes)(method: quotes.reflect.Symbol): Map[quotes.reflect.Symbol, Expr[Any]] = {
// Copy pasted from Cask.
// https://github.com/com-lihaoyi/cask/blob/65b9c8e4fd528feb71575f6e5ef7b5e2e16abbd9/cask/src-3/cask/router/Macros.scala#L38
import quotes.reflect._

val params = method.paramSymss.flatten
val defaults = collection.mutable.Map.empty[Symbol, Expr[Any]]

val Name = (method.name + """\$default\$(\d+)""").r

val idents = method.owner.tree.asInstanceOf[ClassDef].body
idents.foreach{
case deff @ DefDef(Name(idx), _, _, _) =>
val expr = Ref(deff.symbol).asExpr
defaults += (params(idx.toInt - 1) -> expr)
case _ =>
}

defaults.toMap
}
}
7 changes: 7 additions & 0 deletions mainargs/src-3/ParserForClassCompanionVersionSpecific.scala
Original file line number Diff line number Diff line change
@@ -0,0 +1,7 @@
package mainargs

import scala.language.experimental.macros

private [mainargs] trait ParserForClassCompanionVersionSpecific {
inline def apply[T]: ParserForClass[T] = ${ Macros.parserForClass[T] }
}
5 changes: 5 additions & 0 deletions mainargs/src-3/ParserForMethodsCompanionVersionSpecific.scala
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
package mainargs

private [mainargs] trait ParserForMethodsCompanionVersionSpecific {
inline def apply[B](base: B) : ParserForMethods[B] = ${ Macros.parserForMethods[B]('base) }
}
3 changes: 3 additions & 0 deletions mainargs/src-3/acyclic.scala
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
package acyclic

def skipped = ???
12 changes: 6 additions & 6 deletions mainargs/src/Parser.scala
Original file line number Diff line number Diff line change
@@ -1,9 +1,11 @@
package mainargs

import acyclic.skipped

import scala.language.experimental.macros
import java.io.PrintStream
object ParserForMethods{
def apply[B](base: B): ParserForMethods[B] = macro Macros.parserForMethods[B]
}

object ParserForMethods extends ParserForMethodsCompanionVersionSpecific
class ParserForMethods[B](val mains: MethodMains[B]){
def helpText(totalWidth: Int = 100,
docsOnNewLine: Boolean = false,
Expand Down Expand Up @@ -102,9 +104,7 @@ class ParserForMethods[B](val mains: MethodMains[B]){
}
}

object ParserForClass{
def apply[T]: ParserForClass[T] = macro Macros.parserForClass[T]
}
object ParserForClass extends ParserForClassCompanionVersionSpecific
class ParserForClass[T](val mains: ClassMains[T]) extends SubParser[T]{
def helpText(totalWidth: Int = 100,
docsOnNewLine: Boolean = false,
Expand Down
6 changes: 3 additions & 3 deletions mainargs/src/TokensReader.scala
Original file line number Diff line number Diff line change
Expand Up @@ -18,7 +18,7 @@ object TokensReader{
implicit object FloatRead extends TokensReader[Float]("float", strs => tryEither(strs.last.toFloat))
implicit object DoubleRead extends TokensReader[Double]("double", strs => tryEither(strs.last.toDouble))

implicit def OptionRead[T: TokensReader] = new TokensReader[Option[T]](
implicit def OptionRead[T: TokensReader]: TokensReader[Option[T]] = new TokensReader[Option[T]](
implicitly[TokensReader[T]].shortName,
strs => {
strs.lastOption match{
Expand All @@ -31,7 +31,7 @@ object TokensReader{
},
allowEmpty = true
)
implicit def SeqRead[C[_] <: Iterable[_], T: TokensReader](implicit factory: Factory[T, C[T]]) = new TokensReader[C[T]](
implicit def SeqRead[C[_] <: Iterable[_], T: TokensReader](implicit factory: Factory[T, C[T]]): TokensReader[C[T]] = new TokensReader[C[T]](
implicitly[TokensReader[T]].shortName,
strs => {
strs
Expand All @@ -50,7 +50,7 @@ object TokensReader{
alwaysRepeatable = true,
allowEmpty = true
)
implicit def MapRead[K: TokensReader, V: TokensReader] = new TokensReader[Map[K, V]](
implicit def MapRead[K: TokensReader, V: TokensReader]: TokensReader[Map[K, V]] = new TokensReader[Map[K, V]](
"k=v",
strs => {
strs.foldLeft[Either[String, Map[K, V]]](Right(Map())){
Expand Down
Loading