Try to diagnose NoDescriptorForDeclarationException in completion
This commit is contained in:
@@ -22,12 +22,8 @@ import org.jetbrains.kotlin.context.ModuleContext
|
||||
import org.jetbrains.kotlin.extensions.StorageComponentContainerContributor
|
||||
import org.jetbrains.kotlin.incremental.components.LookupTracker
|
||||
import org.jetbrains.kotlin.resolve.*
|
||||
import org.jetbrains.kotlin.resolve.lazy.FileScopeProvider
|
||||
import org.jetbrains.kotlin.resolve.lazy.KotlinCodeAnalyzer
|
||||
import org.jetbrains.kotlin.resolve.lazy.NoTopLevelDescriptorProvider
|
||||
import org.jetbrains.kotlin.resolve.lazy.ResolveSession
|
||||
import org.jetbrains.kotlin.resolve.lazy.*
|
||||
import org.jetbrains.kotlin.resolve.lazy.declarations.DeclarationProviderFactory
|
||||
import org.jetbrains.kotlin.resolve.scopes.SyntheticScopes
|
||||
import org.jetbrains.kotlin.types.expressions.DeclarationScopeProviderForLocalClassifierAnalyzer
|
||||
import org.jetbrains.kotlin.types.expressions.LocalClassDescriptorHolder
|
||||
import org.jetbrains.kotlin.types.expressions.LocalLazyDeclarationResolver
|
||||
@@ -90,6 +86,7 @@ fun createContainerForLazyBodyResolve(
|
||||
useInstance(kotlinCodeAnalyzer.getFileScopeProvider())
|
||||
useInstance(bodyResolveCache)
|
||||
useImpl<LazyTopDownAnalyzerForTopLevel>()
|
||||
useImpl<BasicAbsentDescriptorHandler>()
|
||||
}
|
||||
|
||||
fun createContainerForLazyLocalClassifierAnalyzer(
|
||||
|
||||
@@ -20,10 +20,12 @@ import org.jetbrains.kotlin.container.StorageComponentContainer
|
||||
import org.jetbrains.kotlin.container.useImpl
|
||||
import org.jetbrains.kotlin.container.useInstance
|
||||
import org.jetbrains.kotlin.resolve.lazy.CompilerLocalDescriptorResolver
|
||||
import org.jetbrains.kotlin.resolve.lazy.BasicAbsentDescriptorHandler
|
||||
|
||||
object CompilerEnvironment : TargetEnvironment("Compiler") {
|
||||
override fun configure(container: StorageComponentContainer) {
|
||||
container.useInstance(BodyResolveCache.ThrowException)
|
||||
container.useImpl<CompilerLocalDescriptorResolver>()
|
||||
container.useImpl<BasicAbsentDescriptorHandler>()
|
||||
}
|
||||
}
|
||||
+13
-3
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2010-2015 JetBrains s.r.o.
|
||||
* Copyright 2010-2016 JetBrains s.r.o.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@@ -16,8 +16,18 @@
|
||||
|
||||
package org.jetbrains.kotlin.resolve.lazy
|
||||
|
||||
import org.jetbrains.kotlin.descriptors.DeclarationDescriptor
|
||||
import org.jetbrains.kotlin.psi.KtDeclaration
|
||||
import org.jetbrains.kotlin.psi.psiUtil.getElementTextWithContext
|
||||
|
||||
class NoDescriptorForDeclarationException(declaration: KtDeclaration) :
|
||||
IllegalStateException("Descriptor wasn't found for declaration $declaration\n${declaration.getElementTextWithContext()}")
|
||||
interface AbsentDescriptorHandler {
|
||||
fun diagnoseDescriptorNotFound(declaration: KtDeclaration): DeclarationDescriptor
|
||||
}
|
||||
|
||||
class BasicAbsentDescriptorHandler : AbsentDescriptorHandler {
|
||||
override fun diagnoseDescriptorNotFound(declaration: KtDeclaration) = throw NoDescriptorForDeclarationException(declaration)
|
||||
}
|
||||
|
||||
class NoDescriptorForDeclarationException @JvmOverloads constructor(declaration: KtDeclaration, additionalDetails: String? = null) :
|
||||
IllegalStateException("Descriptor wasn't found for declaration $declaration\n${declaration.getElementTextWithContext()}"
|
||||
+ (additionalDetails?.let { "\n---------------------------------------------------\n$it" } ?: ""))
|
||||
+5
-2
@@ -41,6 +41,7 @@ import java.util.List;
|
||||
public class LazyDeclarationResolver {
|
||||
|
||||
@NotNull private final TopLevelDescriptorProvider topLevelDescriptorProvider;
|
||||
@NotNull private final AbsentDescriptorHandler absentDescriptorHandler;
|
||||
@NotNull private final BindingTrace trace;
|
||||
|
||||
protected DeclarationScopeProvider scopeProvider;
|
||||
@@ -55,9 +56,11 @@ public class LazyDeclarationResolver {
|
||||
public LazyDeclarationResolver(
|
||||
@NotNull GlobalContext globalContext,
|
||||
@NotNull BindingTrace delegationTrace,
|
||||
@NotNull TopLevelDescriptorProvider topLevelDescriptorProvider
|
||||
@NotNull TopLevelDescriptorProvider topLevelDescriptorProvider,
|
||||
@NotNull AbsentDescriptorHandler absentDescriptorHandler
|
||||
) {
|
||||
this.topLevelDescriptorProvider = topLevelDescriptorProvider;
|
||||
this.absentDescriptorHandler = absentDescriptorHandler;
|
||||
LockBasedLazyResolveStorageManager lockBasedLazyResolveStorageManager =
|
||||
new LockBasedLazyResolveStorageManager(globalContext.getStorageManager());
|
||||
|
||||
@@ -233,7 +236,7 @@ public class LazyDeclarationResolver {
|
||||
}
|
||||
}, null);
|
||||
if (result == null) {
|
||||
throw new NoDescriptorForDeclarationException(declaration);
|
||||
return absentDescriptorHandler.diagnoseDescriptorNotFound(declaration);
|
||||
}
|
||||
return result;
|
||||
}
|
||||
|
||||
+3
-2
@@ -166,8 +166,9 @@ class LocalLazyDeclarationResolver(
|
||||
globalContext: GlobalContext,
|
||||
trace: BindingTrace,
|
||||
private val localClassDescriptorManager: LocalClassDescriptorHolder,
|
||||
topLevelDescriptorProvider : TopLevelDescriptorProvider
|
||||
) : LazyDeclarationResolver(globalContext, trace, topLevelDescriptorProvider) {
|
||||
topLevelDescriptorProvider : TopLevelDescriptorProvider,
|
||||
absentDescriptorHandler: AbsentDescriptorHandler
|
||||
) : LazyDeclarationResolver(globalContext, trace, topLevelDescriptorProvider, absentDescriptorHandler) {
|
||||
|
||||
override fun getClassDescriptor(classOrObject: KtClassOrObject, location: LookupLocation): ClassDescriptor {
|
||||
if (localClassDescriptorManager.isMyClass(classOrObject)) {
|
||||
|
||||
@@ -24,5 +24,6 @@ object IdeaEnvironment : TargetEnvironment("Idea") {
|
||||
override fun configure(container: StorageComponentContainer) {
|
||||
container.useImpl<ResolveElementCache>()
|
||||
container.useImpl<IdeaLocalDescriptorResolver>()
|
||||
container.useImpl<IdeaAbsentDescriptorHandler>()
|
||||
}
|
||||
}
|
||||
+18
-3
@@ -17,18 +17,33 @@
|
||||
package org.jetbrains.kotlin.idea.project
|
||||
|
||||
import org.jetbrains.kotlin.descriptors.DeclarationDescriptor
|
||||
import org.jetbrains.kotlin.idea.stubindex.resolve.PluginDeclarationProviderFactory
|
||||
import org.jetbrains.kotlin.psi.KtDeclaration
|
||||
import org.jetbrains.kotlin.resolve.BindingContext
|
||||
import org.jetbrains.kotlin.resolve.lazy.BodyResolveMode
|
||||
import org.jetbrains.kotlin.resolve.lazy.LocalDescriptorResolver
|
||||
import org.jetbrains.kotlin.resolve.lazy.AbsentDescriptorHandler
|
||||
import org.jetbrains.kotlin.resolve.lazy.NoDescriptorForDeclarationException
|
||||
import org.jetbrains.kotlin.resolve.lazy.declarations.DeclarationProviderFactory
|
||||
|
||||
class IdeaLocalDescriptorResolver(
|
||||
private val resolveElementCache: ResolveElementCache
|
||||
): LocalDescriptorResolver {
|
||||
private val resolveElementCache: ResolveElementCache,
|
||||
private val absentDescriptorHandler: AbsentDescriptorHandler
|
||||
) : LocalDescriptorResolver {
|
||||
override fun resolveLocalDeclaration(declaration: KtDeclaration): DeclarationDescriptor {
|
||||
val context = resolveElementCache.resolveToElement(declaration, BodyResolveMode.FULL)
|
||||
return context.get(BindingContext.DECLARATION_TO_DESCRIPTOR, declaration)
|
||||
?: throw NoDescriptorForDeclarationException(declaration)
|
||||
?: absentDescriptorHandler.diagnoseDescriptorNotFound(declaration)
|
||||
}
|
||||
}
|
||||
|
||||
class IdeaAbsentDescriptorHandler(
|
||||
private val declarationProviderFactory: DeclarationProviderFactory
|
||||
) : AbsentDescriptorHandler {
|
||||
override fun diagnoseDescriptorNotFound(declaration: KtDeclaration): DeclarationDescriptor {
|
||||
throw NoDescriptorForDeclarationException(
|
||||
declaration,
|
||||
(declarationProviderFactory as? PluginDeclarationProviderFactory)?.debugToString()
|
||||
)
|
||||
}
|
||||
}
|
||||
+20
@@ -58,4 +58,24 @@ class PluginDeclarationProviderFactory(
|
||||
throw IllegalStateException("Cannot find package fragment for file ${file.name} with package ${file.packageFqName}, " +
|
||||
"vFile ${file.virtualFile}, nonIndexed ${file in nonIndexedFiles}")
|
||||
}
|
||||
|
||||
// trying to diagnose org.jetbrains.kotlin.resolve.lazy.NoDescriptorForDeclarationException in completion
|
||||
private val onCreationDebugInfo = debugInfo()
|
||||
|
||||
fun debugToString(): String {
|
||||
return "PluginDeclarationProviderFactory\nOn failure:\n${debugInfo()}On creation:\n$onCreationDebugInfo"
|
||||
}
|
||||
|
||||
private fun debugInfo(): String {
|
||||
if (nonIndexedFiles.isEmpty()) return "-no synthetic files-\n"
|
||||
|
||||
return buildString {
|
||||
nonIndexedFiles.forEach {
|
||||
append(it.name)
|
||||
append(" isPhysical=${it.isPhysical}")
|
||||
append(" modStamp=${it.modificationStamp}")
|
||||
appendln()
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user