diff --git a/compiler/frontend/src/org/jetbrains/jet/lang/types/expressions/LabelResolver.java b/compiler/frontend/src/org/jetbrains/jet/lang/types/expressions/LabelResolver.java index 0028c8c19da..8f3755a0d18 100644 --- a/compiler/frontend/src/org/jetbrains/jet/lang/types/expressions/LabelResolver.java +++ b/compiler/frontend/src/org/jetbrains/jet/lang/types/expressions/LabelResolver.java @@ -24,6 +24,7 @@ import org.jetbrains.jet.lang.descriptors.*; import org.jetbrains.jet.lang.psi.*; import org.jetbrains.jet.lang.resolve.BindingContext; import org.jetbrains.jet.lang.resolve.BindingContextUtils; +import org.jetbrains.jet.lang.resolve.DescriptorResolver; import org.jetbrains.jet.lang.resolve.name.LabelName; import java.util.Collection; @@ -151,6 +152,13 @@ public class LabelResolver { context.trace.record(LABEL_TARGET, targetLabel, element); context.trace.record(REFERENCE_TARGET, thisReference, declarationDescriptor); + if (declarationDescriptor instanceof ClassDescriptor) { + ClassDescriptor classDescriptor = (ClassDescriptor) declarationDescriptor; + if (!DescriptorResolver.checkHasOuterClassInstance(context.scope, context.trace, targetLabel, classDescriptor)) { + return LabeledReceiverResolutionResult.labelResolutionFailed(); + } + } + return LabeledReceiverResolutionResult.labelResolutionSuccess(thisReceiver); } else if (size == 0) { diff --git a/compiler/testData/codegen/classes/outerThis.jet b/compiler/testData/codegen/classes/outerThis.jet index 123fde68b46..346e44ecbbf 100644 --- a/compiler/testData/codegen/classes/outerThis.jet +++ b/compiler/testData/codegen/classes/outerThis.jet @@ -1,5 +1,5 @@ class Outer() { - class Inner() { + inner class Inner() { val outer: Outer get() = this@Outer } diff --git a/compiler/testData/codegen/regressions/kt2566_2.kt b/compiler/testData/codegen/regressions/kt2566_2.kt index fbde08c2a8e..678109cea3f 100644 --- a/compiler/testData/codegen/regressions/kt2566_2.kt +++ b/compiler/testData/codegen/regressions/kt2566_2.kt @@ -3,13 +3,13 @@ open class A { } open class B : A() { - class E { + inner class E { val foo: String = super@B.foo } } class C : B() { - class D { + inner class D { val foo: String = super@C.foo } } diff --git a/compiler/testData/codegen/super/enclosedFun.jet b/compiler/testData/codegen/super/enclosedFun.jet index f67349f1d4d..1bc7a0a7640 100644 --- a/compiler/testData/codegen/super/enclosedFun.jet +++ b/compiler/testData/codegen/super/enclosedFun.jet @@ -14,7 +14,7 @@ open class N() : M(), K { override fun x() : Int = 20 - open class C() : K { + open inner class C() : K { fun test1() = x() fun test2() = super@N.x() fun test3() = super@N.x() diff --git a/compiler/testData/codegen/super/innerClassLabeledSuper.kt b/compiler/testData/codegen/super/innerClassLabeledSuper.kt index 472baa7c6b3..9d405bd2317 100644 --- a/compiler/testData/codegen/super/innerClassLabeledSuper.kt +++ b/compiler/testData/codegen/super/innerClassLabeledSuper.kt @@ -11,7 +11,7 @@ class A : K { override fun foo() = "A.foo" override fun bar() = "A.bar" - class B : K { + inner class B : K { override fun foo() = "B.foo" override fun bar() = "B.bar" diff --git a/compiler/testData/codegen/super/innerClassLabeledSuperProperty.kt b/compiler/testData/codegen/super/innerClassLabeledSuperProperty.kt index 28a5ffdf5c6..4f4a62f8850 100644 --- a/compiler/testData/codegen/super/innerClassLabeledSuperProperty.kt +++ b/compiler/testData/codegen/super/innerClassLabeledSuperProperty.kt @@ -11,7 +11,7 @@ class A : K() { override val foo = "A.foo" override fun bar() = "A.bar" - class B : K() { + inner class B : K() { override val foo = "B.foo" override fun bar() = "B.bar" diff --git a/compiler/testData/diagnostics/tests/LValueAssignment.kt b/compiler/testData/diagnostics/tests/LValueAssignment.kt index 79bba0a6e66..9acf7d52c6c 100644 --- a/compiler/testData/diagnostics/tests/LValueAssignment.kt +++ b/compiler/testData/diagnostics/tests/LValueAssignment.kt @@ -29,7 +29,7 @@ class C() : B() { fun getInt() = 0 class D() { - class B() { + inner class B() { fun foo() { this@D = D() } diff --git a/compiler/testData/diagnostics/tests/backingField/kt462BackingFieldsResolve.kt b/compiler/testData/diagnostics/tests/backingField/kt462BackingFieldsResolve.kt index 773971716b9..d0b5a63d6b6 100644 --- a/compiler/testData/diagnostics/tests/backingField/kt462BackingFieldsResolve.kt +++ b/compiler/testData/diagnostics/tests/backingField/kt462BackingFieldsResolve.kt @@ -109,7 +109,7 @@ class TestBackingFieldsVisibility() { val x = $namespaceLevelVar - class Inner() { + inner class Inner() { val z = this@TestBackingFieldsVisibility.$x } @@ -169,4 +169,4 @@ class T() { } } } -} \ No newline at end of file +} diff --git a/compiler/testData/diagnostics/tests/inner/innerThisSuper.kt b/compiler/testData/diagnostics/tests/inner/innerThisSuper.kt new file mode 100644 index 00000000000..d281a90a3bc --- /dev/null +++ b/compiler/testData/diagnostics/tests/inner/innerThisSuper.kt @@ -0,0 +1,20 @@ +trait Trait { + fun bar() = 42 +} + +class Outer : Trait { + class Nested { + val t = this@Outer.bar() + val s = super@Outer.bar() + + inner class NestedInner { + val t = this@Outer.bar() + val s = super@Outer.bar() + } + } + + inner class Inner { + val t = this@Outer.bar() + val s = super@Outer.bar() + } +} diff --git a/compiler/testData/diagnostics/tests/inner/localThisSuper.kt b/compiler/testData/diagnostics/tests/inner/localThisSuper.kt new file mode 100644 index 00000000000..a2c87bc61e5 --- /dev/null +++ b/compiler/testData/diagnostics/tests/inner/localThisSuper.kt @@ -0,0 +1,23 @@ +trait Trait { + fun bar() = 42 +} + +class Outer : Trait { + fun foo() { + val t = this@Outer + val s = super@Outer.bar() + + class Local : Trait { + val t = this@Outer + val s = super@Outer.bar() + + inner class Inner { + val t = this@Local + val s = super@Local.bar() + + val tt = this@Outer + val ss = super@Outer.bar() + } + } + } +} diff --git a/compiler/testData/diagnostics/tests/inner/nestedVsInnerAccessOuterMember.kt b/compiler/testData/diagnostics/tests/inner/nestedVsInnerAccessOuterMember.kt index 0b43bfb3158..16615466d7a 100644 --- a/compiler/testData/diagnostics/tests/inner/nestedVsInnerAccessOuterMember.kt +++ b/compiler/testData/diagnostics/tests/inner/nestedVsInnerAccessOuterMember.kt @@ -5,15 +5,21 @@ class Outer { class Nested { fun f() = function() fun g() = property + fun h() = this@Outer.function() + fun i() = this@Outer.property } inner class Inner { fun innerFun() = function() val innerProp = property + fun innerThisFun() = this@Outer.function() + val innerThisProp = this@Outer.property inner class InnerInner { fun f() = innerFun() fun g() = innerProp + fun h() = this@Inner.innerFun() + fun i() = this@Inner.innerProp } } } diff --git a/compiler/testData/diagnostics/tests/thisAndSuper/Super.kt b/compiler/testData/diagnostics/tests/thisAndSuper/Super.kt index 531c75fb2c3..7ff05bd175c 100644 --- a/compiler/testData/diagnostics/tests/thisAndSuper/Super.kt +++ b/compiler/testData/diagnostics/tests/thisAndSuper/Super.kt @@ -27,7 +27,7 @@ class A() : C(), T { super@B.bar() } - class B : T { + inner class B : T { fun test() { super.foo(); super<C>.bar() diff --git a/compiler/testData/diagnostics/tests/thisAndSuper/thisInFunctionLiterals.kt b/compiler/testData/diagnostics/tests/thisAndSuper/thisInFunctionLiterals.kt index 0aa0380a515..c6d8ce909cf 100644 --- a/compiler/testData/diagnostics/tests/thisAndSuper/thisInFunctionLiterals.kt +++ b/compiler/testData/diagnostics/tests/thisAndSuper/thisInFunctionLiterals.kt @@ -1,5 +1,5 @@ class A(val a:Int) { - class B() { + inner class B() { fun Char.xx() : Any { this : Char val a = { diff --git a/compiler/testData/diagnostics/tests/thisAndSuper/thisInNestedClasses.kt b/compiler/testData/diagnostics/tests/thisAndSuper/thisInInnerClasses.kt similarity index 87% rename from compiler/testData/diagnostics/tests/thisAndSuper/thisInNestedClasses.kt rename to compiler/testData/diagnostics/tests/thisAndSuper/thisInInnerClasses.kt index b88da281e4c..8691aa32a93 100644 --- a/compiler/testData/diagnostics/tests/thisAndSuper/thisInNestedClasses.kt +++ b/compiler/testData/diagnostics/tests/thisAndSuper/thisInInnerClasses.kt @@ -1,6 +1,6 @@ class A(val a:Int) { - class B() { + inner class B() { val x = this@B : B val y = this@A : A val z = this : B diff --git a/compiler/testData/resolve/Super.jet b/compiler/testData/resolve/Super.jet index 10b1995e229..75e54307ee8 100644 --- a/compiler/testData/resolve/Super.jet +++ b/compiler/testData/resolve/Super.jet @@ -14,7 +14,7 @@ `C`super@A.bar() } - class B : T { + inner class B : T { fun test() { `T`super.foo(); `C`super@A.bar() diff --git a/compiler/tests/org/jetbrains/jet/checkers/JetDiagnosticsTestGenerated.java b/compiler/tests/org/jetbrains/jet/checkers/JetDiagnosticsTestGenerated.java index 74c6949f454..3b22cbee93d 100644 --- a/compiler/tests/org/jetbrains/jet/checkers/JetDiagnosticsTestGenerated.java +++ b/compiler/tests/org/jetbrains/jet/checkers/JetDiagnosticsTestGenerated.java @@ -2419,6 +2419,11 @@ public class JetDiagnosticsTestGenerated extends AbstractDiagnosticsTestWithEage doTest("compiler/testData/diagnostics/tests/inner/extensionFun.kt"); } + @TestMetadata("innerThisSuper.kt") + public void testInnerThisSuper() throws Exception { + doTest("compiler/testData/diagnostics/tests/inner/innerThisSuper.kt"); + } + @TestMetadata("localClass.kt") public void testLocalClass() throws Exception { doTest("compiler/testData/diagnostics/tests/inner/localClass.kt"); @@ -2429,6 +2434,11 @@ public class JetDiagnosticsTestGenerated extends AbstractDiagnosticsTestWithEage doTest("compiler/testData/diagnostics/tests/inner/localClassInsideNested.kt"); } + @TestMetadata("localThisSuper.kt") + public void testLocalThisSuper() throws Exception { + doTest("compiler/testData/diagnostics/tests/inner/localThisSuper.kt"); + } + @TestMetadata("modality.kt") public void testModality() throws Exception { doTest("compiler/testData/diagnostics/tests/inner/modality.kt"); @@ -4063,9 +4073,9 @@ public class JetDiagnosticsTestGenerated extends AbstractDiagnosticsTestWithEage doTest("compiler/testData/diagnostics/tests/thisAndSuper/thisInFunctionLiterals.kt"); } - @TestMetadata("thisInNestedClasses.kt") - public void testThisInNestedClasses() throws Exception { - doTest("compiler/testData/diagnostics/tests/thisAndSuper/thisInNestedClasses.kt"); + @TestMetadata("thisInInnerClasses.kt") + public void testThisInInnerClasses() throws Exception { + doTest("compiler/testData/diagnostics/tests/thisAndSuper/thisInInnerClasses.kt"); } @TestMetadata("thisInPropertyInitializer.kt") diff --git a/idea/testData/checker/QualifiedThisInClosures.kt b/idea/testData/checker/QualifiedThisInClosures.kt index 8419b66f281..ea3eba9fc00 100644 --- a/idea/testData/checker/QualifiedThisInClosures.kt +++ b/idea/testData/checker/QualifiedThisInClosures.kt @@ -1,6 +1,6 @@ class A(val a:Int) { - class B() { + inner class B() { val x = this@B : B val y = this@A : A val z = this : B