diff --git a/java/java-psi-api/src/com/intellij/util/JavaTypeNullabilityUtil.java b/java/java-psi-api/src/com/intellij/util/JavaTypeNullabilityUtil.java index 3885a20b6dfc..b908e024bddc 100644 --- a/java/java-psi-api/src/com/intellij/util/JavaTypeNullabilityUtil.java +++ b/java/java-psi-api/src/com/intellij/util/JavaTypeNullabilityUtil.java @@ -21,13 +21,6 @@ import java.util.Set; */ @ApiStatus.Internal public final class JavaTypeNullabilityUtil { - /** - * Java allows recursive type bounds, e.g. {@code class A> {}}. - * During the nullability conflict it may turn into the endless recursion. - * This field limits the depth of the recursive type parameters. - */ - private static final int MAX_NULLABILITY_CONFLICT_RECURSION_PARAMETER_DEPTH = 100; - /** * Computes the class type nullability * @@ -114,17 +107,13 @@ public final class JavaTypeNullabilityUtil { public static @NotNull NullabilityConflict getNullabilityConflictInAssignment(@Nullable PsiType leftType, @Nullable PsiType rightType, boolean checkNotNullToNull) { - return getNullabilityConflictInAssignment(leftType, rightType, 0, checkNotNullToNull, false); + return getNullabilityConflictInAssignment(leftType, rightType, checkNotNullToNull, false); } private static @NotNull NullabilityConflict getNullabilityConflictInAssignment(@Nullable PsiType leftType, @Nullable PsiType rightType, - int recursionDepth, boolean checkNotNullToNull, boolean checkConflictInInitialType) { - if (recursionDepth >= MAX_NULLABILITY_CONFLICT_RECURSION_PARAMETER_DEPTH) { - return NullabilityConflict.UNKNOWN; - } if (checkConflictInInitialType) { NullabilityConflict nullabilityConflict = getNullabilityConflictType(leftType, rightType); if (isAllowedNullabilityConflictType(checkNotNullToNull, nullabilityConflict)) return nullabilityConflict; @@ -137,34 +126,34 @@ public final class JavaTypeNullabilityUtil { } if (rightType instanceof PsiIntersectionType) { - return getNullabilityConflictInTypeArguments(leftType, rightType, recursionDepth, checkNotNullToNull); + return getNullabilityConflictInTypeArguments(leftType, rightType, checkNotNullToNull); } if (rightType instanceof PsiCapturedWildcardType) { - return getNullabilityConflictInAssignment(leftType, ((PsiCapturedWildcardType)rightType).getUpperBound(true), recursionDepth + 1, checkNotNullToNull, + return getNullabilityConflictInAssignment(leftType, ((PsiCapturedWildcardType)rightType).getUpperBound(true), checkNotNullToNull, false); } if (leftType instanceof PsiCapturedWildcardType) { - return getNullabilityConflictInAssignment(((PsiCapturedWildcardType)leftType).getLowerBound(), rightType, recursionDepth + 1, checkNotNullToNull, false); + return getNullabilityConflictInAssignment(((PsiCapturedWildcardType)leftType).getLowerBound(), rightType, checkNotNullToNull, false); } if (leftType instanceof PsiWildcardType) { - return getNullabilityConflictInAssignment(GenericsUtil.getWildcardBound(leftType), rightType, recursionDepth + 1, checkNotNullToNull, false); + return getNullabilityConflictInAssignment(GenericsUtil.getWildcardBound(leftType), rightType, checkNotNullToNull, false); } if (rightType instanceof PsiWildcardType) { - return getNullabilityConflictInAssignment(leftType, GenericsUtil.getWildcardBound(rightType), recursionDepth + 1, checkNotNullToNull, false); + return getNullabilityConflictInAssignment(leftType, GenericsUtil.getWildcardBound(rightType), checkNotNullToNull, false); } if (leftType instanceof PsiArrayType && rightType instanceof PsiArrayType) { return getNullabilityConflictInAssignment(((PsiArrayType)leftType).getComponentType(), - ((PsiArrayType)rightType).getComponentType(), recursionDepth + 1, checkNotNullToNull, true); + ((PsiArrayType)rightType).getComponentType(), checkNotNullToNull, true); } if (!(leftType instanceof PsiClassType) || !(rightType instanceof PsiClassType)) { return NullabilityConflict.UNKNOWN; } - return getNullabilityConflictInTypeArguments(leftType, rightType, recursionDepth, checkNotNullToNull); + return getNullabilityConflictInTypeArguments(leftType, rightType, checkNotNullToNull); } /** @@ -178,10 +167,11 @@ public final class JavaTypeNullabilityUtil { */ private static @NotNull NullabilityConflict getNullabilityConflictInTypeArguments(@NotNull PsiType leftType, @NotNull PsiType rightType, - int recursionDepth, boolean checkNotNullToNull) { + if (isRawType(leftType) || isRawType(rightType)) return NullabilityConflict.UNKNOWN; PsiClass leftClass = PsiTypesUtil.getPsiClass(leftType); if (leftClass == null) return NullabilityConflict.UNKNOWN; + List leftParameterTypeList = getParentParameterTypeListFromDerivedType(leftType, leftClass); List rightParameterTypeList = getParentParameterTypeListFromDerivedType(rightType, leftClass); if (leftParameterTypeList == null || @@ -197,7 +187,6 @@ public final class JavaTypeNullabilityUtil { NullabilityConflict nullabilityConflict = getNullabilityConflictInAssignment( leftParameterType, rightParameterType, - recursionDepth + 1, checkNotNullToNull, true ); @@ -207,6 +196,10 @@ public final class JavaTypeNullabilityUtil { return NullabilityConflict.UNKNOWN; } + private static boolean isRawType(@NotNull PsiType type) { + return type instanceof PsiClassType && ((PsiClassType)type).isRaw(); + } + private static @Nullable List<@NotNull PsiType> getParentParameterTypeListFromDerivedType(@NotNull PsiType derivedType, @NotNull PsiClass superClass) { if (derivedType instanceof PsiIntersectionType) {