From e85ff6f47f91d809a2767dbd50eb2c3c8e8ca177 Mon Sep 17 00:00:00 2001 From: Anna Kozlova Date: Thu, 18 Feb 2016 16:16:25 +0100 Subject: [PATCH] check class accessible from another module: don't check parameters but check if method return type/param types are accessible --- .../impl/analysis/GenericsHighlightUtil.java | 61 ++++++++++++++++--- .../impl/analysis/HighlightVisitorImpl.java | 2 +- ...edTypeOfVariableImplementsUnknownType.java | 10 ++- ...edTypeOfVariableImplementsUnknownType.java | 6 +- 4 files changed, 67 insertions(+), 12 deletions(-) diff --git a/java/java-analysis-impl/src/com/intellij/codeInsight/daemon/impl/analysis/GenericsHighlightUtil.java b/java/java-analysis-impl/src/com/intellij/codeInsight/daemon/impl/analysis/GenericsHighlightUtil.java index 67b77e18aae8..03101dbb85f3 100644 --- a/java/java-analysis-impl/src/com/intellij/codeInsight/daemon/impl/analysis/GenericsHighlightUtil.java +++ b/java/java-analysis-impl/src/com/intellij/codeInsight/daemon/impl/analysis/GenericsHighlightUtil.java @@ -1414,19 +1414,63 @@ public class GenericsHighlightUtil { } static HighlightInfo areSupersAccessible(@NotNull PsiClass aClass) { - return areSupersAccessible(aClass, aClass.getResolveScope(), HighlightNamesUtil.getClassDeclarationTextRange(aClass)); + return areSupersAccessible(aClass, aClass.getResolveScope(), HighlightNamesUtil.getClassDeclarationTextRange(aClass), true); } - static HighlightInfo areSupersAccessible(@NotNull PsiClass aClass, PsiElement ref) { - return areSupersAccessible(aClass, ref.getResolveScope(), ref.getTextRange()); + static HighlightInfo areSupersAccessible(@NotNull PsiClass aClass, PsiReferenceExpression ref) { + final GlobalSearchScope resolveScope = ref.getResolveScope(); + final HighlightInfo info = areSupersAccessible(aClass, resolveScope, ref.getTextRange(), false); + if (info != null) { + return info; + } + + String message = null; + final PsiElement parent = ref.getParent(); + if (parent instanceof PsiMethodCallExpression) { + final JavaResolveResult resolveResult = ((PsiMethodCallExpression)parent).resolveMethodGenerics(); + final PsiMethod method = (PsiMethod)resolveResult.getElement(); + if (method != null) { + final HashSet classes = new HashSet<>(); + final JavaPsiFacade facade = JavaPsiFacade.getInstance(aClass.getProject()); + final PsiSubstitutor substitutor = resolveResult.getSubstitutor(); + + message = isSuperTypeAccessible(substitutor.substitute(method.getReturnType()), classes, false, resolveScope, facade); + if (message == null) { + for (PsiType type : method.getSignature(substitutor).getParameterTypes()) { + + message = isSuperTypeAccessible(type, classes, false, resolveScope, facade); + if (message != null) { + break; + } + } + } + } + } + else { + final PsiElement resolve = ref.resolve(); + if (resolve instanceof PsiField) { + message = isSuperTypeAccessible(((PsiField)resolve).getType(), new HashSet<>(), false, resolveScope, JavaPsiFacade.getInstance(aClass.getProject())); + } + } + + if (message != null) { + return HighlightInfo.newHighlightInfo(HighlightInfoType.ERROR) + .descriptionAndTooltip(message) + .range(ref.getTextRange()) + .create(); + } + + + return null; } private static HighlightInfo areSupersAccessible(@NotNull PsiClass aClass, GlobalSearchScope resolveScope, - TextRange range) { + TextRange range, + boolean checkParameters) { final JavaPsiFacade factory = JavaPsiFacade.getInstance(aClass.getProject()); for (PsiClassType superType : aClass.getSuperTypes()) { - final String notAccessibleErrorMessage = isSuperTypeAccessible(superType, new HashSet(), resolveScope, factory); + final String notAccessibleErrorMessage = isSuperTypeAccessible(superType, new HashSet(), checkParameters, resolveScope, factory); if (notAccessibleErrorMessage != null) { return HighlightInfo.newHighlightInfo(HighlightInfoType.ERROR) .descriptionAndTooltip(notAccessibleErrorMessage) @@ -1440,6 +1484,7 @@ public class GenericsHighlightUtil { @Nullable private static String isSuperTypeAccessible(PsiType superType, HashSet classes, + boolean checkParameters, GlobalSearchScope resolveScope, JavaPsiFacade factory) { final PsiClass aClass = PsiUtil.resolveClassInType(superType); @@ -1449,9 +1494,9 @@ public class GenericsHighlightUtil { return "Cannot access " + HighlightUtil.formatClass(aClass); } - if (superType instanceof PsiClassType) { + if (checkParameters && superType instanceof PsiClassType) { for (PsiType psiType : ((PsiClassType)superType).getParameters()) { - final String notAccessibleMessage = isSuperTypeAccessible(psiType, classes, resolveScope, factory); + final String notAccessibleMessage = isSuperTypeAccessible(psiType, classes, checkParameters, resolveScope, factory); if (notAccessibleMessage != null) { return notAccessibleMessage; } @@ -1459,7 +1504,7 @@ public class GenericsHighlightUtil { } for (PsiClassType type : aClass.getSuperTypes()) { - final String notAccessibleMessage = isSuperTypeAccessible(type, classes, resolveScope, factory); + final String notAccessibleMessage = isSuperTypeAccessible(type, classes, checkParameters, resolveScope, factory); if (notAccessibleMessage != null) { return notAccessibleMessage; } diff --git a/java/java-analysis-impl/src/com/intellij/codeInsight/daemon/impl/analysis/HighlightVisitorImpl.java b/java/java-analysis-impl/src/com/intellij/codeInsight/daemon/impl/analysis/HighlightVisitorImpl.java index 3ab8bda62615..c99c7dd4ad6e 100644 --- a/java/java-analysis-impl/src/com/intellij/codeInsight/daemon/impl/analysis/HighlightVisitorImpl.java +++ b/java/java-analysis-impl/src/com/intellij/codeInsight/daemon/impl/analysis/HighlightVisitorImpl.java @@ -1246,7 +1246,7 @@ public class HighlightVisitorImpl extends JavaElementVisitor implements Highligh } final PsiClass psiClass = PsiUtil.resolveClassInType(type); if (psiClass != null) { - myHolder.add(GenericsHighlightUtil.areSupersAccessible(psiClass, qualifierExpression)); + myHolder.add(GenericsHighlightUtil.areSupersAccessible(psiClass, expression)); } } } diff --git a/java/java-tests/testData/codeInsight/multipleJdks/java7/p/DeclaredTypeOfVariableImplementsUnknownType.java b/java/java-tests/testData/codeInsight/multipleJdks/java7/p/DeclaredTypeOfVariableImplementsUnknownType.java index 1ae112f77d57..04012ce23c3c 100644 --- a/java/java-tests/testData/codeInsight/multipleJdks/java7/p/DeclaredTypeOfVariableImplementsUnknownType.java +++ b/java/java-tests/testData/codeInsight/multipleJdks/java7/p/DeclaredTypeOfVariableImplementsUnknownType.java @@ -1,10 +1,16 @@ package p; abstract class B { void f(A a) { - a.foo(); + a.foo(); + + Object o = a; + + a.bar(); + + a.myField; } void f(java.util.List a) { - a.get(0).foo(); + a.get(0).foo(); } } \ No newline at end of file diff --git a/java/java-tests/testData/codeInsight/multipleJdks/java8/p/DeclaredTypeOfVariableImplementsUnknownType.java b/java/java-tests/testData/codeInsight/multipleJdks/java8/p/DeclaredTypeOfVariableImplementsUnknownType.java index 07e72962683a..f22c03b06c50 100644 --- a/java/java-tests/testData/codeInsight/multipleJdks/java8/p/DeclaredTypeOfVariableImplementsUnknownType.java +++ b/java/java-tests/testData/codeInsight/multipleJdks/java8/p/DeclaredTypeOfVariableImplementsUnknownType.java @@ -3,5 +3,9 @@ import java.util.stream.Stream; import java.util.List; public abstract class A implements List> { - public void foo() {} + public Stream foo() {} + + public void bar() {} + + public Stream myField; } \ No newline at end of file