JavaDescriptorResolver supports resolving classes by PSI elements, not by FqNames

This commit is contained in:
Andrey Breslav
2014-05-13 14:40:00 +04:00
parent 6c5d974284
commit 87750d633c
3 changed files with 37 additions and 13 deletions
@@ -23,6 +23,7 @@ import org.jetbrains.jet.lang.descriptors.ModuleDescriptor;
import org.jetbrains.jet.lang.descriptors.PackageFragmentDescriptor; import org.jetbrains.jet.lang.descriptors.PackageFragmentDescriptor;
import org.jetbrains.jet.lang.descriptors.PackageFragmentProvider; import org.jetbrains.jet.lang.descriptors.PackageFragmentProvider;
import org.jetbrains.jet.lang.resolve.java.lazy.LazyJavaPackageFragmentProvider; import org.jetbrains.jet.lang.resolve.java.lazy.LazyJavaPackageFragmentProvider;
import org.jetbrains.jet.lang.resolve.java.structure.JavaClass;
import org.jetbrains.jet.lang.resolve.name.FqName; import org.jetbrains.jet.lang.resolve.name.FqName;
import org.jetbrains.jet.lang.resolve.name.Name; import org.jetbrains.jet.lang.resolve.name.Name;
import org.jetbrains.jet.lang.types.DependencyClassByQualifiedNameResolver; import org.jetbrains.jet.lang.types.DependencyClassByQualifiedNameResolver;
@@ -55,6 +56,11 @@ public class JavaDescriptorResolver implements DependencyClassByQualifiedNameRes
return lazyJavaPackageFragmentProvider.getClass(qualifiedName); return lazyJavaPackageFragmentProvider.getClass(qualifiedName);
} }
@Nullable
public ClassDescriptor resolveClass(@NotNull JavaClass javaClass) {
return lazyJavaPackageFragmentProvider.getClass(javaClass);
}
@Nullable @Nullable
public PackageFragmentDescriptor getPackageFragment(@NotNull FqName fqName) { public PackageFragmentDescriptor getPackageFragment(@NotNull FqName fqName) {
return lazyJavaPackageFragmentProvider.getPackageFragment(fqName); return lazyJavaPackageFragmentProvider.getPackageFragment(fqName);
@@ -27,7 +27,9 @@ import org.jetbrains.jet.lang.resolve.java.resolver.DescriptorResolverUtils
import org.jetbrains.jet.lang.resolve.java.resolver.JavaPackageFragmentProvider import org.jetbrains.jet.lang.resolve.java.resolver.JavaPackageFragmentProvider
import org.jetbrains.jet.lang.resolve.java.lazy.descriptors.LazyJavaPackageFragment import org.jetbrains.jet.lang.resolve.java.lazy.descriptors.LazyJavaPackageFragment
import org.jetbrains.jet.lang.resolve.kotlin.KotlinJvmBinaryClass import org.jetbrains.jet.lang.resolve.kotlin.KotlinJvmBinaryClass
import org.jetbrains.jet.lang.resolve.scopes.JetScope import org.jetbrains.jet.storage.MemoizedFunctionToNotNull
import org.jetbrains.jet.lang.resolve.java.lazy.descriptors.LazyJavaClassDescriptor
import org.jetbrains.kotlin.util.sure
public class LazyJavaPackageFragmentProvider( public class LazyJavaPackageFragmentProvider(
outerContext: GlobalJavaResolverContext, outerContext: GlobalJavaResolverContext,
@@ -67,6 +69,22 @@ public class LazyJavaPackageFragmentProvider(
} }
} }
private val topLevelClasses = c.storageManager.createMemoizedFunctionWithNullableValues @lambda {
(jClass: JavaClass): LazyJavaClassDescriptor? ->
val fqName = jClass.getFqName()
if (fqName == null) return@lambda null
val packageFragment = getPackageFragment(fqName.parent())
if (packageFragment == null) return@lambda null
LazyJavaClassDescriptor(
c.withTypes(TypeParameterResolver.EMPTY),
packageFragment,
fqName,
jClass
)
}
override fun getPackageFragment(fqName: FqName) = _packageFragments(fqName) override fun getPackageFragment(fqName: FqName) = _packageFragments(fqName)
override fun getPackageFragments(fqName: FqName) = getPackageFragment(fqName)?.let {listOf(it)}.orEmpty() override fun getPackageFragments(fqName: FqName) = getPackageFragment(fqName)?.let {listOf(it)}.orEmpty()
@@ -76,6 +94,7 @@ public class LazyJavaPackageFragmentProvider(
override fun getClassNamesInPackage(packageName: FqName) = getPackageFragment(packageName)?.getMemberScope()?.getAllClassNames().orEmpty() override fun getClassNamesInPackage(packageName: FqName) = getPackageFragment(packageName)?.getMemberScope()?.getAllClassNames().orEmpty()
fun getClass(fqName: FqName): ClassDescriptor? = c.javaClassResolver.resolveClassByFqName(fqName) fun getClass(fqName: FqName): ClassDescriptor? = c.javaClassResolver.resolveClassByFqName(fqName)
fun getClass(javaClass: JavaClass): ClassDescriptor? = c.javaClassResolver.resolveClass(javaClass)
internal val resolveKotlinBinaryClass = c.storageManager.createMemoizedFunctionWithNullableValues { internal val resolveKotlinBinaryClass = c.storageManager.createMemoizedFunctionWithNullableValues {
(kotlinClass: KotlinJvmBinaryClass) -> c.deserializedDescriptorResolver.resolveClass(kotlinClass) (kotlinClass: KotlinJvmBinaryClass) -> c.deserializedDescriptorResolver.resolveClass(kotlinClass)
@@ -94,18 +113,13 @@ public class LazyJavaPackageFragmentProvider(
return c.javaResolverCache.getClassResolvedFromSource(fqName) return c.javaResolverCache.getClassResolvedFromSource(fqName)
} }
} }
val resolvedClassifier = getContainingScope(javaClass)?.getClassifier(javaClass.getName())
return resolvedClassifier as? ClassDescriptor ?: c.javaResolverCache.getClass(javaClass)
}
private fun getContainingScope(javaClass: JavaClass): JetScope? {
val outerClass = javaClass.getOuterClass() val outerClass = javaClass.getOuterClass()
if (outerClass != null) { if (outerClass == null) {
return resolveClass(outerClass)?.getUnsubstitutedInnerClassesScope() return topLevelClasses(javaClass)
}
else {
return getPackageFragment(javaClass.getFqName()!!.parent())?.getMemberScope()
} }
val outerClassScope = resolveClass(outerClass)?.getUnsubstitutedInnerClassesScope()
val nestedClass = outerClassScope?.getClassifier(javaClass.getName()) as? ClassDescriptor
return nestedClass ?: c.javaResolverCache.getClass(javaClass)
} }
override fun resolveClassByFqName(fqName: FqName): ClassDescriptor? { override fun resolveClassByFqName(fqName: FqName): ClassDescriptor? {
@@ -54,8 +54,12 @@ public abstract class LazyJavaPackageFragmentScope(
val cached = c.javaResolverCache.getClass(jClass) val cached = c.javaResolverCache.getClass(jClass)
if (cached != null) if (cached != null)
cached cached
else else {
LazyJavaClassDescriptor(c.withTypes(TypeParameterResolver.EMPTY), packageFragment, fqName, jClass) val classDescriptor = c.javaClassResolver.resolveClass(jClass)
assert(classDescriptor == null || classDescriptor.getContainingDeclaration() == packageFragment,
"Wrong package fragment for $classDescriptor, expected $packageFragment")
classDescriptor
}
} }
} }