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

private inline methods can't call abstract inline methods #19738

Open
felher opened this issue Feb 19, 2024 · 1 comment
Open

private inline methods can't call abstract inline methods #19738

felher opened this issue Feb 19, 2024 · 1 comment

Comments

@felher
Copy link
Contributor

felher commented Feb 19, 2024

Compiler version

3.3.1 (and all current RCs as far as I can tell)

Minimized code

trait SomeTrait:
  inline def base: Unit

  inline def doSomething: Unit = doSomethingHelper
  private inline def doSomethingHelper: Unit = base

object Impl extends SomeTrait:
  inline def base: Unit = ()

object Main:
  Impl.doSomething

Output

[error] -- Error: /tmp/test/src/main/scala/Main.scala:11:7 -----------------------------
[error] 11 |  Impl.doSomething
[error]    |  ^^^^^^^^^^^^^^^^
[error]    |  Deferred inline method base in trait SomeTrait cannot be invoked

Expectation

Should compile

Shallow Investigation

I didn't look into this deeply, but maybe the problem has to do with how the support for calling private inline methods is currently handled (see #15075). It works by remapping Select trees if they are private inline methods:

case tree @ Select(qual: This, name) if tree.symbol.is(Private) && tree.symbol.isInlineMethod =>
  // ... 
  cpy.Select(tree)(qual.asInstance(qual.tpe.widen), name)

which basically rewrites the code

inline def doSomething: Unit = doSomethingHelper

to

inline def doSomething: Unit = this.asInstanceOf[SomeTrait].doSomethingHelper

and I assume this leads the Inliner to select the abstract definition in SomeTrait later on, not the one on Impl. Of course, abstract inline methods can't be invoked directly, so when the compiler reaches private def inlineIfNeeded in Inliner.scala, both the Deferred and Inline flags are set and the above error is given.

@felher felher added itype:bug stat:needs triage Every issue needs to have an "area" and "itype" label labels Feb 19, 2024
@Gedochao Gedochao added area:inline and removed stat:needs triage Every issue needs to have an "area" and "itype" label labels Apr 3, 2024
@smarter
Copy link
Member

smarter commented Jan 8, 2025

private inline is a can of worm, I wonder if we shouldn't deprecate it and recommend private[C] inline instead to avoid this and other problems.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

No branches or pull requests

3 participants