Open
Description
Compiler versions
3.7.2-RC1-bin-20250510-f784625-NIGHTLY
3.7.0
3.6.4
Minimized code
trait A:
inline def foo: Int
given a: A with
override inline def foo: Int = 1
summon[A]/*(using a)*/.foo // 1
/*transparent*/ inline def summonAAndFoo: Int = summonInline[A].foo
summonAAndFoo //doesn't compile: Deferred inline method foo in trait A cannot be invoked
Output
summon[A]
seems to return an implicit of precise type a.type
.
But summonInline[A]
seems to return just A
upon inlining, that's why Deferred inline method foo in trait A cannot be invoked
.
Is this expected behavior?
The output with scalacOptions ++= Seq( "-Xprint-types", "-Vprint:typer")
:
//[info] <<println:((x: Any): Unit)>(
//[info] <<<<App.a:App.a>:App.a.type>:App.a.type>.foo:=> Int>):Unit>
//[info] inline def summonAAndFoo: Int =
//[info] <
//[info] <<<scala.compiletime.summonInline:([T]: T)>[App.A]:App.A>.foo:
//[info] (=> Int)>
//[info] :Int:Int>
//[info] <<println:((x: Any): Unit)>(<App.summonAAndFoo:=> Int>):Unit>
The output with scalacOptions ++= Seq( "-Xprint-types", "-Vprint:inlining")
:
[info] <<println:((x: Any): Unit)>(<<<1:(1 : Int)> :Int:Int>:Int>):Unit>
[info] inline def summonAAndFoo: Int =
[info] <
[info] <<<scala.compiletime.summonInline:([T]: T)>[App.A]:App.A>.foo:
[info] (=> Int)>
[info] :Int:Int>
[info] <<println:((x: Any): Unit)>(<<<<App.a:App.a>.foo:<error>> :Int:Int>:Int>
[info] ):Unit>
Expectation
summonAAndFoo
should compile and return 1
.
Discovered in https://stackoverflow.com/questions/79614883/how-to-call-an-inline-method-from-within-a-scala-3-6-4-macro
Activity
readren commentedon May 12, 2025
Shouldn't be a
Expr.summonInline
method that returns precise type too. That would allow a macro that summons a generic type-class to get a singleton instance and call its transparent inline overriden methods to obtains constants.Gedochao commentedon May 15, 2025
cc @bishabosha @jchyb
bishabosha commentedon May 15, 2025
I'd ask @nicolasstucki if possible from the ether
jchyb commentedon May 15, 2025
Calling
scala.compiletime.summonInline[A].foo
directly (not from an inline method) works without an error. To me this seems like a bug in the compiler (more specifically, we recheck typing after inlining with some custom logic - it's probably there).About the second question, the difference between a summon and summonInline is that the second one is delayed until when Inlining happens. So Expr.summon will work like summon in transparent inline macros (because it summons in the same compiler phase as summon), and like summonInline in nontransparent macros (because it summons in the same phase as summonInline) - so there would be no use adding Expr.summonInline