Skip to content

Commit 2ac151f

Browse files
committed
Fix nested inference
1 parent a6af724 commit 2ac151f

2 files changed

Lines changed: 53 additions & 23 deletions

File tree

org.eclipse.jdt.core.compiler.batch/src/org/eclipse/jdt/internal/compiler/lookup/InferenceContext18.java

Lines changed: 35 additions & 23 deletions
Original file line numberDiff line numberDiff line change
@@ -425,8 +425,8 @@ public BoundSet inferInvocationType(TypeBinding expectedType, InvocationSite inv
425425
if (!addConstraintsToC(this.invocationArguments, c, method, this.inferenceKind, invocationSite))
426426
return null;
427427
// 5. bullet: determine B4 from C
428-
List<Set<InferenceVariable>> components = this.currentBounds.computeConnectedComponents(this.inferenceVariables);
429428
while (!c.isEmpty()) {
429+
List<Set<InferenceVariable>> components = this.currentBounds.computeConnectedComponents(this.inferenceVariables);
430430
// *
431431
Set<ConstraintFormula> bottomSet = findBottomSet(c, allOutputVariables(c), components);
432432
if (bottomSet.isEmpty()) {
@@ -460,6 +460,12 @@ public BoundSet inferInvocationType(TypeBinding expectedType, InvocationSite inv
460460
if (!this.currentBounds.reduceOneConstraint(this, constraint))
461461
return null;
462462
}
463+
for (ConstraintFormula constraint : bottomSet) {
464+
// https://bugs.openjdk.org/browse/JDK-8052325
465+
if (constraint instanceof ConstraintExpressionFormula expressionFormula && expressionFormula.left instanceof LambdaExpression lambda && lambda.argumentsTypeElided()) {
466+
addLambdaConstraintsToC(lambda, c, method, expressionFormula.right);
467+
}
468+
}
463469
}
464470
// 6. bullet: solve
465471
BoundSet solution = solve();
@@ -645,6 +651,31 @@ private boolean addConstraintsToC(Expression[] exprs, Set<ConstraintFormula> c,
645651
return true;
646652
}
647653

654+
private boolean addLambdaConstraintsToC(LambdaExpression lambda, Set<ConstraintFormula> c, MethodBinding method, TypeBinding substF)
655+
throws InferenceFailureException
656+
{
657+
// https://bugs.openjdk.java.net/browse/JDK-8038747
658+
BlockScope skope = lambda.enclosingScope;
659+
if (substF.isFunctionalInterface(skope)) { // could be an inference variable.
660+
ReferenceBinding t = (ReferenceBinding) substF;
661+
ParameterizedTypeBinding withWildCards = InferenceContext18.parameterizedWithWildcard(t);
662+
if (withWildCards != null) {
663+
t = ConstraintExpressionFormula.findGroundTargetType(this, skope, lambda, withWildCards);
664+
}
665+
MethodBinding functionType;
666+
if (t != null && (functionType = t.getSingleAbstractMethod(skope, true)) != null && (lambda = lambda.resolveExpressionExpecting(t, this.scope)) != null) {
667+
TypeBinding r = functionType.returnType;
668+
Expression[] resultExpressions = lambda.resultExpressions();
669+
for (int i = 0, length = resultExpressions == null ? 0 : resultExpressions.length; i < length; i++) {
670+
Expression resultExpression = resultExpressions[i];
671+
if (!addConstraintsToC_OneExpr(resultExpression, c, r.original(), r, method))
672+
return false;
673+
}
674+
}
675+
}
676+
return true;
677+
}
678+
648679
private boolean addConstraintsToC_OneExpr(Expression expri, Set<ConstraintFormula> c, TypeBinding fsi, TypeBinding substF, MethodBinding method)
649680
throws InferenceFailureException
650681
{
@@ -659,27 +690,9 @@ private boolean addConstraintsToC_OneExpr(Expression expri, Set<ConstraintFormul
659690
}
660691
if (expri instanceof FunctionalExpression) {
661692
c.add(new ConstraintExceptionFormula((FunctionalExpression) expri, substF));
662-
if (expri instanceof LambdaExpression) {
663-
// https://bugs.openjdk.java.net/browse/JDK-8038747
664-
LambdaExpression lambda = (LambdaExpression) expri;
665-
BlockScope skope = lambda.enclosingScope;
666-
if (substF.isFunctionalInterface(skope)) { // could be an inference variable.
667-
ReferenceBinding t = (ReferenceBinding) substF;
668-
ParameterizedTypeBinding withWildCards = InferenceContext18.parameterizedWithWildcard(t);
669-
if (withWildCards != null) {
670-
t = ConstraintExpressionFormula.findGroundTargetType(this, skope, lambda, withWildCards);
671-
}
672-
MethodBinding functionType;
673-
if (t != null && (functionType = t.getSingleAbstractMethod(skope, true)) != null && (lambda = lambda.resolveExpressionExpecting(t, this.scope)) != null) {
674-
TypeBinding r = functionType.returnType;
675-
Expression[] resultExpressions = lambda.resultExpressions();
676-
for (int i = 0, length = resultExpressions == null ? 0 : resultExpressions.length; i < length; i++) {
677-
Expression resultExpression = resultExpressions[i];
678-
if (!addConstraintsToC_OneExpr(resultExpression, c, r.original(), r, method))
679-
return false;
680-
}
681-
}
682-
}
693+
// https://bugs.openjdk.org/browse/JDK-8052325
694+
if (expri instanceof LambdaExpression lambda && !lambda.argumentsTypeElided()) {
695+
addLambdaConstraintsToC(lambda, c, method, substF);
683696
}
684697
} else if (expri instanceof Invocation && expri.isPolyExpression()) {
685698

@@ -709,7 +722,6 @@ private boolean addConstraintsToC_OneExpr(Expression expri, Set<ConstraintFormul
709722
if (!innerContext.computeB3(invocation, substF, shallowMethod))
710723
return false;
711724
if (innerContext.addConstraintsToC(arguments, c, innerMethod.genericMethod(), innerContext.inferenceKind, invocation)) {
712-
this.currentBounds.addBounds(innerContext.currentBounds, this.environment);
713725
return true;
714726
}
715727
return false;

org.eclipse.jdt.core.tests.compiler/src/org/eclipse/jdt/core/tests/compiler/regression/GenericsRegressionTest.java

Lines changed: 18 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -7058,5 +7058,23 @@ interface C<W> {
70587058
},
70597059
"");
70607060
}
7061+
7062+
public void testGH4557() {
7063+
runConformTest(new String[] {
7064+
"Test.java",
7065+
"""
7066+
import java.util.List;
7067+
public class Test {
7068+
public static void main(List<?> l) {
7069+
get(get(get(l)));
7070+
}
7071+
public static <T> List<?> get(List<T> l) {
7072+
return l;
7073+
}
7074+
}
7075+
"""
7076+
},
7077+
"");
7078+
}
70617079
}
70627080

0 commit comments

Comments
 (0)