Skip to content

Binary compatibility and inline accessors #16983

Closed
@nicolasstucki

Description

@nicolasstucki

Compiler version

3.0, 3.1, 3.2, 3.3

Inline accessors

Whenever we refer to a definition that is not public in an inline definition, we generate an inline accessor to access that definition from where the code is inlined.

final class C:
  private def a: Int = 2
  inline def b: Int = a + C.d

object C:
  private[C] val d: Int = 4

is transformed into something like

final class C:
  private def a: Int = 2
  def inline$a = a
  def inline$d = C.d
  inline def b: Int = inline$a + inline$d
object C:
  private[C] val d: Int = 4

Note that the accessors are added to the class using the private definition. This can lead to duplication of accessors.

Issue 1: Changing any definition from private to public is a binary incompatible change

object C:
- private def a: Int = 2
+ def a: Int = 2
  inline def b: Int = a

This change would remove the need to generate C$$inline$a because a is publicly accessible. But any compiled code that inlined b before this change refers to C$$inline$a. This code can be located in different libraries, and we might be unable to recompile it with the new inline definition.

Issue 2: Changing the implementation of an inline definition can be a binary incompatible change

object C:
  private def a: Int = 2
-  inline def b: Int = a
+  inline def b: Int = 3

This change would remove the need to generate C$$inline$a because we never inline a. But any compiled code that inlined b before this change refers to C$$inline$a. This code can be located in different libraries, and we might be unable to recompile it with the new inline definition.

Issue 3: Removing final from a class is a binary incompatible change

- final class C:
+ class C:
  private def a: Int = 2
  inline def b: Int = a

If the class is final a will get the accessor inline$a but if it is not final it gets the accessor C$$inline$a.

Metadata

Metadata

Assignees

Labels

itype:soundnessSoundness bug (it lets us compile code that crashes at runtime with a ClassCastException)

Type

No type

Projects

No projects

Milestone

No milestone

Relationships

None yet

Development

No branches or pull requests

Issue actions