diff --git a/java/java-psi-impl/src/com/intellij/psi/impl/source/resolve/PsiResolveHelperImpl.java b/java/java-psi-impl/src/com/intellij/psi/impl/source/resolve/PsiResolveHelperImpl.java index 13ac4e798d0f..abbd7264958d 100644 --- a/java/java-psi-impl/src/com/intellij/psi/impl/source/resolve/PsiResolveHelperImpl.java +++ b/java/java-psi-impl/src/com/intellij/psi/impl/source/resolve/PsiResolveHelperImpl.java @@ -969,6 +969,19 @@ public class PsiResolveHelperImpl implements PsiResolveHelper { for (int i = 0; i < argExtendsListTypes.length; i++) { PsiClassType argBoundType = argExtendsListTypes[i]; PsiClassType paramBoundType = paramExtendsListTypes[i]; + final PsiClassType.ClassResolveResult argResolveResult = argBoundType.resolveGenerics(); + final PsiClassType.ClassResolveResult paramResolveResult = paramBoundType.resolveGenerics(); + final PsiClass paramBoundClass = paramResolveResult.getElement(); + final PsiClass argBoundClass = argResolveResult.getElement(); + if (argBoundClass != null && paramBoundClass != null && paramBoundClass != argBoundClass) { + if (argBoundClass.isInheritor(paramBoundClass, true)) { + final PsiSubstitutor superClassSubstitutor = + TypeConversionUtil.getSuperClassSubstitutor(paramBoundClass, argBoundClass, argResolveResult.getSubstitutor()); + argBoundType = JavaPsiFacade.getElementFactory(argClass.getProject()).createType(paramBoundClass, superClassSubstitutor); + } else { + return null; + } + } final Pair constraint = getSubstitutionForTypeParameterInner(paramBoundType, argBoundType, patternType, constraintType, depth); if (constraint != null) { diff --git a/java/java-tests/testData/codeInsight/daemonCodeAnalyzer/lambda/graphInference/InferenceFromNotEqualTypeParamsBounds.java b/java/java-tests/testData/codeInsight/daemonCodeAnalyzer/lambda/graphInference/InferenceFromNotEqualTypeParamsBounds.java new file mode 100644 index 000000000000..764acd23750a --- /dev/null +++ b/java/java-tests/testData/codeInsight/daemonCodeAnalyzer/lambda/graphInference/InferenceFromNotEqualTypeParamsBounds.java @@ -0,0 +1,68 @@ +import java.util.*; + +public class ConcurrentCollectors { + static class Test1 { + static > C groupingBy(F f, + C c, + BiConsumer consumer) { + return new CImpl<>(f, consumer, arg(c.getOp())); + } + + static > BiOp arg(BiOp op) { + return null; + } + } + + static class Test2 { + static > C groupingBy(F f, + C c, + BiConsumer consumer) { + return new CImpl<>(f, consumer, arg(c.getOp())); + } + + static > BiOp arg(BiOp op) { + return null; + } + } + + static class Test3 { + static > C groupingBy(F f, + C c, + BiConsumer consumer) { + return new CImpl<>(f, consumer, arg(c.getOp())); + } + + static > BiOp arg(BiOp op) { + return null; + } + } + + + interface C { + BiOp getOp(); + } + + interface F {} + + + static class CImpl implements C { + CImpl(F f, + BiConsumer consumer, + BiOp op) { + } + + @Override + public BiOp getOp() { + return null; + } + } + + interface BiFun { } + + interface BiOp extends BiFun { + } + + interface BiConsumer {} + + interface ConcurrentMap extends Map {} +} diff --git a/java/java-tests/testSrc/com/intellij/codeInsight/daemon/lambda/GraphInferenceHighlightingTest.java b/java/java-tests/testSrc/com/intellij/codeInsight/daemon/lambda/GraphInferenceHighlightingTest.java index d297ab237ba0..22dc4501e91f 100644 --- a/java/java-tests/testSrc/com/intellij/codeInsight/daemon/lambda/GraphInferenceHighlightingTest.java +++ b/java/java-tests/testSrc/com/intellij/codeInsight/daemon/lambda/GraphInferenceHighlightingTest.java @@ -64,6 +64,10 @@ public class GraphInferenceHighlightingTest extends LightDaemonAnalyzerTestCase doTest(); } + public void testInferenceFromNotEqualTypeParamsBounds() throws Exception { + doTest(); + } + public void testSOEDuringInferenceFromParamBounds() throws Exception { doTest(); }