From aa96c6e741b81bc6700088764e1d3ece546176f3 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?S=C3=A9bastien=20Doeraene?= Date: Wed, 22 Nov 2023 16:48:37 +0100 Subject: [PATCH] Work around lampepfl/dotty#19019: patch the SelfDef of inner module classes. Re-create the correct self type which is a term reference to the accompanying lazy val. --- .../reader/tasties/TreeUnpickler.scala | 12 +++++- .../scala/simple_trees/ObjectWithSelf.scala | 43 +++++++++++++++++++ 2 files changed, 54 insertions(+), 1 deletion(-) create mode 100644 test-sources/src/main/scala/simple_trees/ObjectWithSelf.scala diff --git a/tasty-query/shared/src/main/scala/tastyquery/reader/tasties/TreeUnpickler.scala b/tasty-query/shared/src/main/scala/tastyquery/reader/tasties/TreeUnpickler.scala index cfead58b..6409ef61 100644 --- a/tasty-query/shared/src/main/scala/tastyquery/reader/tasties/TreeUnpickler.scala +++ b/tasty-query/shared/src/main/scala/tastyquery/reader/tasties/TreeUnpickler.scala @@ -685,7 +685,17 @@ private[tasties] class TreeUnpickler private ( case _ => readTypeTree } } - val self = readSelf + + val self0 = readSelf + val self = self0 match + case Some(orig @ SelfDef(name, tpt)) if cls.name.isObjectClassTypeName && cls.owner.isClass => + // Work around https://github.com/lampepfl/dotty/issues/19019: replace with a correct SELFDEF + val owner = cls.owner.asClass + val fixedTpt = TypeWrapper(TermRef(owner.thisType, cls.name.sourceObjectName))(orig.pos) + Some(SelfDef(name, fixedTpt)(orig.pos)) + case _ => + self0 + cls.withGivenSelfType(self.map(_.tpt.toType)) // The first entry is the constructor val cstr = readStat.asInstanceOf[DefDef] diff --git a/test-sources/src/main/scala/simple_trees/ObjectWithSelf.scala b/test-sources/src/main/scala/simple_trees/ObjectWithSelf.scala new file mode 100644 index 00000000..b54bc361 --- /dev/null +++ b/test-sources/src/main/scala/simple_trees/ObjectWithSelf.scala @@ -0,0 +1,43 @@ +package simple_trees + +object ObjectWithSelf: + object StaticObjectNoSelf: + def foo: Any = this + def bar: Any = this.foo + end StaticObjectNoSelf + + object StaticObjectWithSelf: + self => + + def foo: Any = self + def bar: Any = self.foo + end StaticObjectWithSelf + + class Container: + object NonStaticObjectNoSelf: + def foo: Any = this + def bar: Any = this.foo + end NonStaticObjectNoSelf + + object NonStaticObjectWithSelf: + self => + + def foo: Any = self + def bar: Any = self.foo // used to cause StackOverflow while resolving this in WholeClasspathSuite tests + end NonStaticObjectWithSelf + end Container + + def methodOwner(): Unit = + object LocalObjectNoSelf: + def foo: Any = this + def bar: Any = this.foo + end LocalObjectNoSelf + + object LocalObjectWithSelf: + self => + + def foo: Any = self + def bar: Any = self.foo + end LocalObjectWithSelf + end methodOwner +end ObjectWithSelf