From 2e4807856f5d5cd31396f75fe41389724b1beb79 Mon Sep 17 00:00:00 2001 From: Alexander Udalov Date: Thu, 21 Nov 2013 16:13:10 +0400 Subject: [PATCH] Don't create NamespaceType for enum entries Enum entry expressions have the type of their enum, so it shouldn't be possible to access static nested classes of enum entries from outside. This fixes BlackBoxCodegenTestGenerated$CallableReference.testEnumNameMethod --- .../resolve/calls/CallExpressionResolver.java | 38 +++++++++++-------- .../dontCreateNamespaceTypeForEnumEntry.kt | 14 +++++++ .../checkers/JetDiagnosticsTestGenerated.java | 5 +++ 3 files changed, 41 insertions(+), 16 deletions(-) create mode 100644 compiler/testData/diagnostics/tests/enum/dontCreateNamespaceTypeForEnumEntry.kt diff --git a/compiler/frontend/src/org/jetbrains/jet/lang/resolve/calls/CallExpressionResolver.java b/compiler/frontend/src/org/jetbrains/jet/lang/resolve/calls/CallExpressionResolver.java index e0be8949ed9..a034abfc1c6 100644 --- a/compiler/frontend/src/org/jetbrains/jet/lang/resolve/calls/CallExpressionResolver.java +++ b/compiler/frontend/src/org/jetbrains/jet/lang/resolve/calls/CallExpressionResolver.java @@ -151,23 +151,29 @@ public class CallExpressionResolver { @NotNull ClassifierDescriptor classifier, @NotNull ResolutionContext context ) { - if (isLHSOfDot(expression) && classifier instanceof ClassDescriptor) { - List scopes = new ArrayList(3); - - scopes.add(classObjectType.getMemberScope()); - scopes.add(getStaticNestedClassesScope((ClassDescriptor) classifier)); - - Name referencedName = expression.getReferencedNameAsName(); - NamespaceDescriptor namespace = context.scope.getNamespace(referencedName); - if (namespace != null) { - //for enums loaded from java binaries - scopes.add(namespace.getMemberScope()); - } - - JetScope scope = new ChainedScope(classifier, scopes.toArray(new JetScope[scopes.size()])); - return new NamespaceType(referencedName, scope, new ExpressionReceiver(expression, classObjectType)); + if (!isLHSOfDot(expression) || !(classifier instanceof ClassDescriptor)) { + return classObjectType; } - return classObjectType; + ClassDescriptor classDescriptor = (ClassDescriptor) classifier; + + if (classDescriptor.getKind() == ClassKind.ENUM_ENTRY) { + return classObjectType; + } + + List scopes = new ArrayList(3); + + scopes.add(classObjectType.getMemberScope()); + scopes.add(getStaticNestedClassesScope(classDescriptor)); + + Name referencedName = expression.getReferencedNameAsName(); + NamespaceDescriptor namespace = context.scope.getNamespace(referencedName); + if (namespace != null) { + //for enums loaded from java binaries + scopes.add(namespace.getMemberScope()); + } + + JetScope scope = new ChainedScope(classifier, scopes.toArray(new JetScope[scopes.size()])); + return new NamespaceType(referencedName, scope, new ExpressionReceiver(expression, classObjectType)); } private boolean furtherNameLookup( diff --git a/compiler/testData/diagnostics/tests/enum/dontCreateNamespaceTypeForEnumEntry.kt b/compiler/testData/diagnostics/tests/enum/dontCreateNamespaceTypeForEnumEntry.kt new file mode 100644 index 00000000000..3835008d4e1 --- /dev/null +++ b/compiler/testData/diagnostics/tests/enum/dontCreateNamespaceTypeForEnumEntry.kt @@ -0,0 +1,14 @@ +enum class E { + FIRST + SECOND { + class A + } +} + +val foo: Any.() -> Unit = {} + +fun f1() = E.FIRST.foo() +fun f2() = E.FIRST.(foo)() +fun f3() = E.SECOND.foo() +fun f4() = E.SECOND.(foo)() +fun f5() = E.SECOND.A() diff --git a/compiler/tests/org/jetbrains/jet/checkers/JetDiagnosticsTestGenerated.java b/compiler/tests/org/jetbrains/jet/checkers/JetDiagnosticsTestGenerated.java index 816e5e10d99..129a1657917 100644 --- a/compiler/tests/org/jetbrains/jet/checkers/JetDiagnosticsTestGenerated.java +++ b/compiler/tests/org/jetbrains/jet/checkers/JetDiagnosticsTestGenerated.java @@ -2532,6 +2532,11 @@ public class JetDiagnosticsTestGenerated extends AbstractDiagnosticsTestWithEage JetTestUtils.assertAllTestsPresentByMetadata(this.getClass(), "org.jetbrains.jet.generators.tests.GenerateTests", new File("compiler/testData/diagnostics/tests/enum"), Pattern.compile("^(.+)\\.kt$"), true); } + @TestMetadata("dontCreateNamespaceTypeForEnumEntry.kt") + public void testDontCreateNamespaceTypeForEnumEntry() throws Exception { + doTest("compiler/testData/diagnostics/tests/enum/dontCreateNamespaceTypeForEnumEntry.kt"); + } + @TestMetadata("entryShouldBeOfEnumType.kt") public void testEntryShouldBeOfEnumType() throws Exception { doTest("compiler/testData/diagnostics/tests/enum/entryShouldBeOfEnumType.kt");