Make computation of arguments for raw types lazy

See how we translate raw types to Kotlin model:
RawType(A) = A<ErasedUpperBound(T1), ...>
ErasedUpperBound(T : G<t>) = G<*> // UpperBound(T) is a type G<t> with arguments
ErasedUpperBound(T : A) = A // UpperBound(T) is a type A without arguments
ErasedUpperBound(T : F) = UpperBound(F) // UB(T) is another type parameter F

Stack overflow happens with the following classes:
class A<X extends B> // NB: raw type B in upper bound
class B<Y extends A> // NB: raw type A in upper bound

when calculating raw type for A, we start calculate ErasedUpperBound(Y),
thus starting calculating raw type for B => ErasedUpperBound(X) => RawType(A),
so we have SOE here.
The problem is that we calculating the arguments for these raw types eagerly,
while from the definition of ErasedUpperBound(Y) we only need a type constructor
of raw type B (and the number of parameters), we don't use its arguments.

The solution is to make arguments calculating for raw types lazy

 #KT-16528 Fixed
This commit is contained in:
Denis Zharkov
2017-03-09 17:14:52 +03:00
parent f2fea9a04a
commit 7173e56393
7 changed files with 90 additions and 2 deletions
@@ -0,0 +1,19 @@
// FILE: JavaScriptParser.java
public class JavaScriptParser<T extends JSPsiTypeParser> {
public String foo() {return "OK";}
}
// FILE: JSPsiTypeParser.java
public class JSPsiTypeParser<T extends JavaScriptParser> {}
// FILE: ES6Parser.java
public class ES6Parser<T extends JSPsiTypeParser> extends JavaScriptParser<T> {}
// FILE: main.kt
fun createParser(): JavaScriptParser<*> {
return ES6Parser<JSPsiTypeParser<*>>()
}
fun box(): String = createParser().foo()
@@ -0,0 +1,21 @@
// WITH_RUNTIME
// FILE: Device.java
import java.util.Collection;
public class Device<D extends Device, S extends Service> {
public static Collection<Device<Device, Service>> getLoop() {
return null;
}
}
// FILE: Service.java
public class Service<D extends Device, S extends Service> {
}
// FILE: loop.kt
fun box(): String {
val x = Device.getLoop()?.firstOrNull() // compilation error
return "OK"
}