Skip to content

2.13.1 scalac StackOverflowError when annotation argument references the annottee #11870

@dbarvitsky

Description

@dbarvitsky

Consider the example:

class Invariant(condition: Unit => Boolean) extends scala.annotation.StaticAnnotation
abstract class Demo {
  @Invariant( _ => x.length == 3 )
  def x: String = "foo"
}

This code results in the java.lang.StackOverflowError through scala.reflect.internal.AnnotationInfos$LazyAnnotationInfo.forcedInfo$lzycompute(AnnotationInfos.scala:158) (scalac-SOE-stack.txt has the full stack trace if you need it). As far as I can tell, the stack trace is different from those encountered in #7449, #1632, #1667 and #10421. Increasing the stack -Xss128m just makes the SOE stack trace longer, so it looks like cyclic init.

Some pointers to help narrow the problem.

  1. The annotation argument does not have to be a lambda. The following snippet yields the same SOE:
class Annot(arg: Any) extends scala.annotation.StaticAnnotation
abstract class Demo {
  @Annot(x)
  def x: String = "foo"
}
  1. The following example compiles fine.
class Annot(arg: Any) extends scala.annotation.StaticAnnotation
abstract class Demo {
  @Annot(y)
  def x: String = "foo"
  def y: String = "bar"
}
  1. However, if you put the annotation on the second field as well, there is the SOE again
class Annot(arg: Any) extends scala.annotation.StaticAnnotation
abstract class Demo {
  @Annot(y)
  def x: String = "foo"

 @Annot(x)
  def y: String = "bar"
}
  1. Finally, the code below causes SOE even when the annotations are different.
class Annot1(arg: Any) extends scala.annotation.StaticAnnotation
class Annot2(arg: Any) extends scala.annotation.StaticAnnotation
abstract class Demo {
  @Annot1(y)
  def x: String = "foo"

  @Annot2(x)
  def y: String = "bar"
}

Thank you!

Metadata

Metadata

Assignees

Type

No type

Projects

No projects

Milestone

Relationships

None yet

Development

No branches or pull requests

Issue actions