Skip to content

Commit 44c1e3a

Browse files
authored
Harden GADT constraint handling to survive illegal F-bounds (#20325)
This currently fails BestEffortCompilationTests The problem is that i20317a.scala contains illegal cyclic references. The cycles cause many different algorithms in the compiler to loop. We normally reject the program, and that's that. But under best-effort, we crash with Stackoverflows in the loops later. What to do? It's not feasible to avoid the looping behavior at acceptable cost. Can we disable best effort under certain conditions?
2 parents 1f3c652 + 5e408bd commit 44c1e3a

File tree

4 files changed

+11
-1
lines changed

4 files changed

+11
-1
lines changed

Diff for: compiler/src/dotty/tools/dotc/core/GadtConstraint.scala

+2-1
Original file line numberDiff line numberDiff line change
@@ -193,7 +193,8 @@ sealed trait GadtState {
193193
case i => pt.paramRefs(i)
194194
case tp => tp
195195
}
196-
196+
if !param.info.exists then
197+
throw TypeError(em"illegal recursive reference involving $param")
197198
val tb = param.info.bounds
198199
tb.derivedTypeBounds(
199200
lo = substDependentSyms(tb.lo, isUpper = false),

Diff for: compiler/test/dotc/neg-best-effort-pickling.blacklist

+1
Original file line numberDiff line numberDiff line change
@@ -13,6 +13,7 @@ curried-dependent-ift.scala
1313
i17121.scala
1414
illegal-match-types.scala
1515
i13780-1.scala
16+
i20317a.scala
1617

1718
# semantic db generation fails in the first compilation
1819
i1642.scala

Diff for: tests/neg/i20317.scala

+3
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,3 @@
1+
type Foo[A] = A
2+
3+
def foo[A <: Foo[A]]: Unit = () // error // error

Diff for: tests/neg/i20317a.scala

+5
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,5 @@
1+
type SemigroupStructural[A] =
2+
A & { def combine(a: A): A }
3+
def combineAll[A <: SemigroupStructural[A]](
4+
i: A, l: List[A]
5+
): A = l.foldLeft(i)(_.combine(_)) // error

0 commit comments

Comments
 (0)