Outer's superclass' method is now inaccessible from nested
Also the diagnostic error message reported the wrong nested class name: it should be the nested class in the hierarchy which is static, not the class of the scope where we're checking the accessibility
This commit is contained in:
@@ -1358,28 +1358,20 @@ public class DescriptorResolver {
|
|||||||
@NotNull PsiElement reportErrorsOn,
|
@NotNull PsiElement reportErrorsOn,
|
||||||
@NotNull ClassDescriptor target
|
@NotNull ClassDescriptor target
|
||||||
) {
|
) {
|
||||||
ClassDescriptor thisClass = getContainingClass(scope);
|
DeclarationDescriptor descriptor = getContainingClass(scope);
|
||||||
if (thisClass == null) return true;
|
while (descriptor != null) {
|
||||||
if (!isAncestor(target, thisClass, true)) return true;
|
if (descriptor instanceof ClassDescriptor) {
|
||||||
|
ClassDescriptor classDescriptor = (ClassDescriptor) descriptor;
|
||||||
if (!hasOuterClassInstance(thisClass, target)) {
|
if (isSubclass(classDescriptor, target)) {
|
||||||
trace.report(INACCESSIBLE_OUTER_CLASS_EXPRESSION.on(reportErrorsOn, thisClass));
|
return true;
|
||||||
return false;
|
}
|
||||||
}
|
if (isStaticNestedClass(classDescriptor)) {
|
||||||
return true;
|
trace.report(INACCESSIBLE_OUTER_CLASS_EXPRESSION.on(reportErrorsOn, classDescriptor));
|
||||||
}
|
return false;
|
||||||
|
}
|
||||||
private static boolean hasOuterClassInstance(@NotNull ClassDescriptor thisClass, @NotNull ClassDescriptor outerClass) {
|
|
||||||
DeclarationDescriptor descriptor = thisClass;
|
|
||||||
while (true) {
|
|
||||||
assert descriptor != null : "outerClass must be an ancestor of thisClass: " + thisClass + " " + outerClass;
|
|
||||||
if (descriptor instanceof ClassDescriptor && isSubclass((ClassDescriptor) descriptor, outerClass)) {
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
if (isStaticNestedClass(descriptor)) {
|
|
||||||
return false;
|
|
||||||
}
|
}
|
||||||
descriptor = descriptor.getContainingDeclaration();
|
descriptor = descriptor.getContainingDeclaration();
|
||||||
}
|
}
|
||||||
|
return true;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -0,0 +1,9 @@
|
|||||||
|
open class Base {
|
||||||
|
fun foo() {}
|
||||||
|
}
|
||||||
|
|
||||||
|
class Derived : Base() {
|
||||||
|
class Nested {
|
||||||
|
fun bar() = <!INACCESSIBLE_OUTER_CLASS_EXPRESSION!>foo()<!>
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -2481,6 +2481,11 @@ public class JetDiagnosticsTestGenerated extends AbstractDiagnosticsTestWithEage
|
|||||||
doTest("compiler/testData/diagnostics/tests/inner/outerProtectedMember.kt");
|
doTest("compiler/testData/diagnostics/tests/inner/outerProtectedMember.kt");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@TestMetadata("outerSuperClassMember.kt")
|
||||||
|
public void testOuterSuperClassMember() throws Exception {
|
||||||
|
doTest("compiler/testData/diagnostics/tests/inner/outerSuperClassMember.kt");
|
||||||
|
}
|
||||||
|
|
||||||
@TestMetadata("traits.kt")
|
@TestMetadata("traits.kt")
|
||||||
public void testTraits() throws Exception {
|
public void testTraits() throws Exception {
|
||||||
doTest("compiler/testData/diagnostics/tests/inner/traits.kt");
|
doTest("compiler/testData/diagnostics/tests/inner/traits.kt");
|
||||||
|
|||||||
@@ -0,0 +1,7 @@
|
|||||||
|
class A {
|
||||||
|
class B {
|
||||||
|
val r = object {
|
||||||
|
fun bar() = this@A
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -0,0 +1,2 @@
|
|||||||
|
<!-- inaccessibleOuterClassExpression1 -->
|
||||||
|
Expression is inaccessible from a nested class 'B', use 'inner' keyword to make the class inner
|
||||||
@@ -98,4 +98,8 @@ public class DiagnosticMessageTest extends JetLiteFixture {
|
|||||||
public void testRenderCollectionOfTypes() throws Exception {
|
public void testRenderCollectionOfTypes() throws Exception {
|
||||||
doTest("renderCollectionOfTypes", 1, Errors.EXPECTED_PARAMETERS_NUMBER_MISMATCH);
|
doTest("renderCollectionOfTypes", 1, Errors.EXPECTED_PARAMETERS_NUMBER_MISMATCH);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public void testInaccessibleOuterClassExpression() throws Exception {
|
||||||
|
doTest("inaccessibleOuterClassExpression", 1, Errors.INACCESSIBLE_OUTER_CLASS_EXPRESSION);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user