Skip to content

Commit 3ab00a8

Browse files
committed
Replace SingleDenotation by SymDenotation after erasure
This is an alternative fix for scala#11303, the downside is that when time-travelling from post-erasure to pre-erasure, we need to recompute the SingleDenotation. This commit passes all tests except tests/pos/t2399.scala which fails compilation from tasty. This could probably be fixed by changing the logic in computeDenot to only run `memberDenot` for opaque types, for other infos we can just use `asSeenFrom` instead.
1 parent c413ea2 commit 3ab00a8

File tree

3 files changed

+26
-4
lines changed

3 files changed

+26
-4
lines changed

compiler/src/dotty/tools/dotc/core/Denotations.scala

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -851,7 +851,10 @@ object Denotations {
851851
else if valid.runId != currentPeriod.runId then
852852
toNewRun
853853
else if currentPeriod.code > valid.code then
854-
goForward
854+
if ctx.erasedTypes && this.isInstanceOf[NonSymSingleDenotation] then
855+
symbol.denot.current
856+
else
857+
goForward
855858
else
856859
goBack
857860
end current

compiler/src/dotty/tools/dotc/core/Types.scala

Lines changed: 13 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -2156,11 +2156,20 @@ object Types {
21562156
lastDenotation match {
21572157
case lastd0: SingleDenotation =>
21582158
val lastd = lastd0.skipRemoved
2159-
if (lastd.validFor.runId == ctx.runId && (checkedPeriod != Nowhere)) finish(lastd.current)
2159+
2160+
val needsRecompute =
2161+
prefix != NoPrefix
2162+
&& lastd.isInstanceOf[SymDenotation]
2163+
&& checkedPeriod.containsPhaseId(erasurePhase.next.id)
2164+
&& !ctx.erasedTypes
2165+
&& ctx.phase.id < checkedPeriod.firstPhaseId
2166+
&& infoDependsOnPrefix(lastd.symbol.denot, prefix)
2167+
2168+
if (lastd.validFor.runId == ctx.runId && (checkedPeriod != Nowhere) && !needsRecompute) finish(lastd.current)
21602169
else lastd match {
21612170
case lastd: SymDenotation =>
2162-
if (stillValid(lastd) && (checkedPeriod != Nowhere)) finish(lastd.current)
2163-
else finish(memberDenot(lastd.initial.name, allowPrivate = false))
2171+
if (stillValid(lastd) && (checkedPeriod != Nowhere) && !needsRecompute) finish(lastd.current)
2172+
else memberDenot(lastd.initial.name, allowPrivate = needsRecompute)
21642173
case _ =>
21652174
fromDesignator
21662175
}
@@ -2299,6 +2308,7 @@ object Types {
22992308
*/
23002309
private def infoDependsOnPrefix(symd: SymDenotation, prefix: Type)(using Context): Boolean =
23012310
symd.maybeOwner.membersNeedAsSeenFrom(prefix) && !symd.is(NonMember)
2311+
|| prefix.isInstanceOf[Types.ThisType] && symd.is(Opaque)
23022312

23032313
/** Is this a reference to a class or object member? */
23042314
def isMemberRef(using Context): Boolean = designator match {

tests/pos/t6231c.scala

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,9 @@
1+
object Bug {
2+
def bar(ev: Any) = {
3+
trait X(val x: Int) {
4+
def qux: () => x.type = { () => println(ev); x }
5+
}
6+
(new X(1) {}).qux()
7+
}
8+
}
9+

0 commit comments

Comments
 (0)