KT-1080 Don't use previously imported packages while resolving import references

This commit is contained in:
svtk
2012-01-20 11:58:17 +04:00
parent 746279ed56
commit 7fae503a38
16 changed files with 195 additions and 82 deletions
@@ -7,6 +7,7 @@ import org.jetbrains.jet.lang.JetSemanticServices;
import org.jetbrains.jet.lang.descriptors.NamespaceDescriptor;
import org.jetbrains.jet.lang.resolve.BindingTrace;
import org.jetbrains.jet.lang.resolve.DescriptorUtils;
import org.jetbrains.jet.lang.resolve.Importer;
import org.jetbrains.jet.lang.resolve.scopes.WritableScope;
/**
@@ -27,10 +28,10 @@ public class JavaBridgeConfiguration implements Configuration {
}
@Override
public void addDefaultImports(@NotNull BindingTrace trace, @NotNull WritableScope rootScope) {
public void addDefaultImports(@NotNull BindingTrace trace, @NotNull WritableScope rootScope, @NotNull Importer importer) {
rootScope.importScope(new JavaPackageScope("", null, javaSemanticServices));
rootScope.importScope(new JavaPackageScope("java.lang", null, javaSemanticServices));
delegateConfiguration.addDefaultImports(trace, rootScope);
importer.addScopeImport(new JavaPackageScope("java.lang", null, javaSemanticServices));
delegateConfiguration.addDefaultImports(trace, rootScope, importer);
}
@Override
@@ -3,6 +3,7 @@ package org.jetbrains.jet.lang;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.jet.lang.descriptors.NamespaceDescriptor;
import org.jetbrains.jet.lang.resolve.BindingTrace;
import org.jetbrains.jet.lang.resolve.Importer;
import org.jetbrains.jet.lang.resolve.scopes.WritableScope;
/**
@@ -11,7 +12,7 @@ import org.jetbrains.jet.lang.resolve.scopes.WritableScope;
public interface Configuration {
Configuration EMPTY = new Configuration() {
@Override
public void addDefaultImports(@NotNull BindingTrace trace, @NotNull WritableScope rootScope) {
public void addDefaultImports(@NotNull BindingTrace trace, @NotNull WritableScope rootScope, @NotNull Importer importer) {
}
@Override
@@ -19,7 +20,7 @@ public interface Configuration {
}
};
void addDefaultImports(@NotNull BindingTrace trace, @NotNull WritableScope rootScope);
void addDefaultImports(@NotNull BindingTrace trace, @NotNull WritableScope rootScope, @NotNull Importer importer);
/**
*
@@ -3,9 +3,9 @@ package org.jetbrains.jet.lang;
import com.intellij.openapi.project.Project;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.jet.lang.descriptors.NamespaceDescriptor;
import org.jetbrains.jet.lang.psi.JetImportDirective;
import org.jetbrains.jet.lang.psi.JetPsiFactory;
import org.jetbrains.jet.lang.resolve.BindingTrace;
import org.jetbrains.jet.lang.resolve.Importer;
import org.jetbrains.jet.lang.resolve.ImportsResolver;
import org.jetbrains.jet.lang.resolve.scopes.WritableScope;
@@ -24,9 +24,9 @@ public class StandardConfiguration implements Configuration {
}
@Override
public void addDefaultImports(@NotNull BindingTrace trace, @NotNull WritableScope rootScope) {
JetImportDirective importDirective = JetPsiFactory.createImportDirective(project, "std.*");
new ImportsResolver.ImportResolver(trace, true).processImportReference(importDirective, rootScope);
public void addDefaultImports(@NotNull BindingTrace trace, @NotNull WritableScope rootScope, @NotNull Importer importer) {
ImportsResolver.ImportResolver importResolver = new ImportsResolver.ImportResolver(trace, true);
importResolver.processImportReference(JetPsiFactory.createImportDirective(project, "std.*"), rootScope, importer);
}
@Override
@@ -215,4 +215,12 @@ public class DescriptorUtils {
}
return null;
}
@Nullable
public static ClassDescriptor getObjectIfObjectOrClassObjectDescriptor(ClassDescriptor descriptor) {
if ((descriptor).getKind() == ClassKind.OBJECT) {
return descriptor;
}
return descriptor.getClassObjectDescriptor();
}
}
@@ -0,0 +1,139 @@
package org.jetbrains.jet.lang.resolve;
import com.google.common.collect.Lists;
import com.intellij.openapi.util.Pair;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.jet.lang.descriptors.*;
import org.jetbrains.jet.lang.resolve.scopes.JetScope;
import org.jetbrains.jet.lang.resolve.scopes.WritableScope;
import org.jetbrains.jet.lang.types.JetType;
import java.util.Collection;
import java.util.List;
/**
* @author svtk
*/
public interface Importer {
void addAllUnderImport(@NotNull DeclarationDescriptor descriptor);
void addAliasImport(@NotNull DeclarationDescriptor descriptor, @NotNull String aliasName);
void addScopeImport(@NotNull JetScope scope);
class StandardImporter implements Importer {
private final WritableScope namespaceScope;
private final boolean firstPhase;
public StandardImporter(WritableScope namespaceScope, boolean firstPhase) {
this.namespaceScope = namespaceScope;
this.firstPhase = firstPhase;
}
@Override
public void addAllUnderImport(@NotNull DeclarationDescriptor descriptor) {
importAllUnderDeclaration(descriptor);
}
@Override
public void addAliasImport(@NotNull DeclarationDescriptor descriptor, @NotNull String aliasName) {
importDeclarationAlias(descriptor, aliasName);
}
@Override
public void addScopeImport(@NotNull JetScope scope) {
importScope(scope);
}
protected void importScope(@NotNull JetScope scope) {
namespaceScope.importScope(scope);
}
protected void importAllUnderDeclaration(@NotNull DeclarationDescriptor descriptor) {
if (descriptor instanceof NamespaceDescriptor) {
namespaceScope.importScope(((NamespaceDescriptor) descriptor).getMemberScope());
}
if (firstPhase) {
if (descriptor instanceof ClassDescriptor) {
ClassDescriptor objectDescriptor = DescriptorUtils.getObjectIfObjectOrClassObjectDescriptor((ClassDescriptor) descriptor);
if (objectDescriptor != null) {
Collection<? extends DeclarationDescriptor> innerClassesAndObjects = objectDescriptor.getInnerClassesAndObjects();
for (DeclarationDescriptor innerClassOrObject : innerClassesAndObjects) {
namespaceScope.importClassifierAlias(innerClassOrObject.getName(), (ClassifierDescriptor) innerClassOrObject);
}
}
}
return;
}
if (descriptor instanceof VariableDescriptor) {
JetType type = ((VariableDescriptor) descriptor).getOutType();
namespaceScope.importScope(type.getMemberScope());
}
else if (descriptor instanceof ClassDescriptor) {
JetType classObjectType = ((ClassDescriptor) descriptor).getClassObjectType();
if (classObjectType != null) {
namespaceScope.importScope(classObjectType.getMemberScope());
}
}
}
protected void importDeclarationAlias(@NotNull DeclarationDescriptor descriptor, @NotNull String aliasName) {
if (descriptor instanceof ClassifierDescriptor) {
namespaceScope.importClassifierAlias(aliasName, (ClassifierDescriptor) descriptor);
}
else if (descriptor instanceof NamespaceDescriptor) {
namespaceScope.importNamespaceAlias(aliasName, (NamespaceDescriptor) descriptor);
}
else if (descriptor instanceof FunctionDescriptor) {
namespaceScope.importFunctionAlias(aliasName, (FunctionDescriptor) descriptor);
}
else if (descriptor instanceof VariableDescriptor) {
namespaceScope.importVariableAlias(aliasName, (VariableDescriptor) descriptor);
}
}
}
class DelayedImporter extends StandardImporter {
private final List<JetScope> scopesToImport = Lists.newArrayList();
private final List<Pair<DeclarationDescriptor, String>> imports = Lists.newArrayList();
public DelayedImporter(@NotNull WritableScope namespaceScope, boolean firstPhase) {
super(namespaceScope, firstPhase);
}
@Override
public void addAllUnderImport(@NotNull DeclarationDescriptor descriptor) {
imports.add(Pair.<DeclarationDescriptor, String>create(descriptor, null));
}
@Override
public void addAliasImport(@NotNull DeclarationDescriptor descriptor, @NotNull String aliasName) {
imports.add(Pair.create(descriptor, aliasName));
}
@Override
public void addScopeImport(@NotNull JetScope scope) {
scopesToImport.add(scope);
}
public void processImports() {
for (JetScope scope : scopesToImport) {
importScope(scope);
}
for (Pair<DeclarationDescriptor, String> anImport : imports) {
DeclarationDescriptor descriptor = anImport.getFirst();
String aliasName = anImport.getSecond();
boolean allUnderImport = aliasName == null;
if (allUnderImport) {
importAllUnderDeclaration(descriptor);
}
else {
importDeclarationAlias(descriptor, aliasName);
}
}
}
}
}
@@ -4,6 +4,7 @@ import com.google.common.base.Predicate;
import com.google.common.collect.Collections2;
import com.google.common.collect.Lists;
import com.google.common.collect.Maps;
import com.intellij.openapi.util.Pair;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;
import org.jetbrains.jet.lang.descriptors.*;
@@ -39,19 +40,21 @@ public class ImportsResolver {
ImportResolver importResolver = new ImportResolver(context.getTrace(), firstPhase);
for (JetFile file : context.getNamespaceDescriptors().keySet()) {
WritableScope namespaceScope = context.getNamespaceScopes().get(file);
Importer.DelayedImporter delayedImporter = new Importer.DelayedImporter(namespaceScope, firstPhase);
if (!firstPhase) {
namespaceScope.clearImports();
}
context.getConfiguration().addDefaultImports(context.getTrace(), namespaceScope);
context.getConfiguration().addDefaultImports(context.getTrace(), namespaceScope, delayedImporter);
Map<JetImportDirective, DeclarationDescriptor> resolvedDirectives = Maps.newHashMap();
List<JetImportDirective> importDirectives = file.getImportDirectives();
for (JetImportDirective importDirective : importDirectives) {
Collection<? extends DeclarationDescriptor> descriptors = importResolver.processImportReference(importDirective, namespaceScope);
Collection<? extends DeclarationDescriptor> descriptors = importResolver.processImportReference(importDirective, namespaceScope, delayedImporter);
if (descriptors != null && descriptors.size() == 1) {
resolvedDirectives.put(importDirective, descriptors.iterator().next());
}
}
delayedImporter.processImports();
if (firstPhase) continue;
for (JetImportDirective importDirective : importDirectives) {
@@ -59,6 +62,7 @@ public class ImportsResolver {
}
}
}
@Nullable
private static JetSimpleNameExpression getLastReference(@NotNull JetExpression importedReference) {
if (importedReference instanceof JetDotQualifiedExpression) {
@@ -123,7 +127,7 @@ public class ImportsResolver {
}
@Nullable
public Collection<? extends DeclarationDescriptor> processImportReference(@NotNull JetImportDirective importDirective, @NotNull WritableScope namespaceScope) {
public Collection<? extends DeclarationDescriptor> processImportReference(@NotNull JetImportDirective importDirective, @NotNull JetScope scope, @NotNull Importer importer) {
if (importDirective.isAbsoluteInRootNamespace()) {
trace.report(UNSUPPORTED.on(importDirective, "TypeHierarchyResolver")); // TODO
return null;
@@ -132,18 +136,18 @@ public class ImportsResolver {
if (importedReference == null) return null;
Collection<? extends DeclarationDescriptor> descriptors;
if (importedReference instanceof JetQualifiedExpression) {
descriptors = lookupDescriptorsForQualifiedExpression((JetQualifiedExpression) importedReference, namespaceScope);
descriptors = lookupDescriptorsForQualifiedExpression((JetQualifiedExpression) importedReference, scope);
}
else {
assert importedReference instanceof JetSimpleNameExpression;
descriptors = lookupDescriptorsForSimpleNameReference((JetSimpleNameExpression) importedReference, namespaceScope, true);
descriptors = lookupDescriptorsForSimpleNameReference((JetSimpleNameExpression) importedReference, scope, true);
}
JetSimpleNameExpression referenceExpression = getLastReference(importedReference);
if (importDirective.isAllUnder()) {
if (referenceExpression == null || !canImportMembersFrom(descriptors, referenceExpression)) return null;
for (DeclarationDescriptor descriptor : descriptors) {
importAllUnderDeclaration(descriptor, namespaceScope);
importer.addAllUnderImport(descriptor);
}
return null;
}
@@ -152,65 +156,11 @@ public class ImportsResolver {
if (aliasName == null) return null;
for (DeclarationDescriptor descriptor : descriptors) {
importDeclarationAlias(namespaceScope, aliasName, descriptor);
importer.addAliasImport(descriptor, aliasName);
}
return descriptors;
}
private void importAllUnderDeclaration(@NotNull DeclarationDescriptor descriptor, @NotNull WritableScope namespaceScope) {
if (firstPhase) {
if (descriptor instanceof NamespaceDescriptor) {
namespaceScope.importScope(((NamespaceDescriptor) descriptor).getMemberScope());
}
if (descriptor instanceof ClassDescriptor) {
ClassDescriptor objectDescriptor = getObjectIfObjectOrClassObjectDescriptor((ClassDescriptor) descriptor);
if (objectDescriptor != null) {
Collection<? extends DeclarationDescriptor> innerClassesAndObjects = objectDescriptor.getInnerClassesAndObjects();
for (DeclarationDescriptor innerClassOrObject : innerClassesAndObjects) {
namespaceScope.importClassifierAlias(innerClassOrObject.getName(), (ClassifierDescriptor) innerClassOrObject);
}
}
}
return;
}
if (descriptor instanceof NamespaceDescriptor) {
namespaceScope.importScope(((NamespaceDescriptor) descriptor).getMemberScope());
}
if (descriptor instanceof VariableDescriptor) {
JetType type = ((VariableDescriptor) descriptor).getOutType();
namespaceScope.importScope(type.getMemberScope());
}
else if (descriptor instanceof ClassDescriptor) {
JetType classObjectType = ((ClassDescriptor) descriptor).getClassObjectType();
if (classObjectType != null) {
namespaceScope.importScope(classObjectType.getMemberScope());
}
}
}
@Nullable
private static ClassDescriptor getObjectIfObjectOrClassObjectDescriptor(ClassDescriptor descriptor) {
if ((descriptor).getKind() == ClassKind.OBJECT) {
return descriptor;
}
return descriptor.getClassObjectDescriptor();
}
private static void importDeclarationAlias(WritableScope namespaceScope, String aliasName, DeclarationDescriptor descriptor) {
if (descriptor instanceof ClassifierDescriptor) {
namespaceScope.importClassifierAlias(aliasName, (ClassifierDescriptor) descriptor);
}
else if (descriptor instanceof NamespaceDescriptor) {
namespaceScope.importNamespaceAlias(aliasName, (NamespaceDescriptor) descriptor);
}
else if (descriptor instanceof FunctionDescriptor) {
namespaceScope.importFunctionAlias(aliasName, (FunctionDescriptor) descriptor);
}
else if (descriptor instanceof VariableDescriptor) {
namespaceScope.importVariableAlias(aliasName, (VariableDescriptor) descriptor);
}
}
@NotNull
private Collection<? extends DeclarationDescriptor> lookupDescriptorsForQualifiedExpression(
@NotNull JetQualifiedExpression importedReference, @NotNull JetScope outerScope) {
@@ -292,7 +242,7 @@ public class ImportsResolver {
@NotNull
private Collection<? extends DeclarationDescriptor> lookupObjectMembers(@NotNull ClassDescriptor classDescriptor, @NotNull JetSimpleNameExpression memberReference) {
if (firstPhase) {
ClassDescriptor objectDescriptor = getObjectIfObjectOrClassObjectDescriptor(classDescriptor);
ClassDescriptor objectDescriptor = DescriptorUtils.getObjectIfObjectOrClassObjectDescriptor(classDescriptor);
if (objectDescriptor == null) return Collections.emptyList();
return getInnerClassesAndObjectsByName(objectDescriptor, memberReference);
}
@@ -2,7 +2,7 @@
// +JDK
import java.*
import util.*
import java.util.*
import <!UNRESOLVED_REFERENCE!>utils<!>.*
import java.io.PrintStream
@@ -1,7 +1,6 @@
// +JDK
import java.*
import util.*
import java.util.*
import java.io.*
@@ -0,0 +1,16 @@
//FILE:a.kt
//+JDK
//KT-1080 Don't use previously imported packages while resolving import references
package kt1080
import <!UNRESOLVED_REFERENCE!>reflect<!>.Constructor
import b.*
import <!UNRESOLVED_REFERENCE!>d<!>
import b.d
//FILE:b.kt
package b.d
@@ -1,5 +1,5 @@
import java.*
import util.*
import java.util.*
fun f_plus(): Int {
var x: Int = 1
+1 -1
View File
@@ -1,5 +1,5 @@
import `java::java`java.*
import `java::java.util`util.*
import java.`java::java.util`util.*
fun foo(~a~a : `std::Array`Array<`std::Int`Int>) : `java::java.util.List`List {
`a`a.`std::Array.get(Int)`get(1)
+1 -1
View File
@@ -1,5 +1,5 @@
import `java::java`java.*
import `java::java.util`util.*
import java.`java::java.util`util.*
~c~fun c(~x~x : java.lang.`java::java.lang.Number`Number) {
`x`x.`java::java.lang.Number.intValue()`intValue()
+1 -1
View File
@@ -1,5 +1,5 @@
import `java::java`java.*
import `java::java.util`util.*
import java.`java::java.util`util.*
class B : `java::java.lang.Object`Object {
fun bar(~o~o : `java::java.lang.Object`Object) {
@@ -1,5 +1,5 @@
import `java::java`java.*
import `java::java.util`util.*
import java.`java::java.util`util.*
fun typeTransform() {
Integer.getInteger("", 239)`:std::Int`
+1 -1
View File
@@ -1,5 +1,5 @@
import java.*
import util.*
import java.util.*
import <error>utils</error>.*
import java.io.PrintStream
@@ -1,5 +1,4 @@
import java.*
import util.*
import java.util.*
import java.io.*