BuilderFactoryForDuplicateSignatureDiagnostics: report diagnostics lazily

This commit is contained in:
Pavel V. Talanov
2015-12-02 16:06:30 +03:00
parent 05a62c5892
commit d20fb5ddd7
2 changed files with 47 additions and 4 deletions
@@ -53,8 +53,18 @@ class BuilderFactoryForDuplicateSignatureDiagnostics(
// Avoid errors when some classes are not loaded for some reason
private val typeMapper = JetTypeMapper(bindingContext, ClassBuilderMode.LIGHT_CLASSES, fileClassesProvider, incrementalCache, moduleName)
private val reportDiagnosticsTasks = ArrayList<() -> Unit>()
fun reportDiagnostics() {
reportDiagnosticsTasks.forEach { it() }
reportDiagnosticsTasks.clear()
}
override fun handleClashingSignatures(data: ConflictingJvmDeclarationsData) {
reportDiagnosticsTasks.add { reportConflictingJvmSignatures(data) }
}
private fun reportConflictingJvmSignatures(data: ConflictingJvmDeclarationsData) {
val noOwnImplementations = data.signatureOrigins.all { it.originKind in EXTERNAL_SOURCES_KINDS }
val elements = LinkedHashSet<PsiElement>()
@@ -82,6 +92,14 @@ class BuilderFactoryForDuplicateSignatureDiagnostics(
classOrigin: JvmDeclarationOrigin,
classInternalName: String?,
signatures: MultiMap<RawSignature, JvmDeclarationOrigin>
) {
reportDiagnosticsTasks.add { reportClashingSignaturesInHierarchy(classOrigin, classInternalName, signatures) }
}
private fun reportClashingSignaturesInHierarchy(
classOrigin: JvmDeclarationOrigin,
classInternalName: String?,
signatures: MultiMap<RawSignature, JvmDeclarationOrigin>
) {
val descriptor = classOrigin.descriptor
if (descriptor !is ClassDescriptor) return
@@ -165,7 +183,7 @@ class BuilderFactoryForDuplicateSignatureDiagnostics(
return groupedBySignature
}
public fun isOrOverridesSamAdapter(descriptor: CallableMemberDescriptor): Boolean {
private fun isOrOverridesSamAdapter(descriptor: CallableMemberDescriptor): Boolean {
if (descriptor is SamAdapterDescriptor<*>) return true
return descriptor.getKind() == CallableMemberDescriptor.Kind.FAKE_OVERRIDE
@@ -17,6 +17,8 @@
package org.jetbrains.kotlin.codegen.state
import com.intellij.openapi.project.Project
import com.intellij.openapi.util.ModificationTracker
import com.intellij.psi.PsiElement
import org.jetbrains.kotlin.builtins.ReflectionTypes
import org.jetbrains.kotlin.codegen.*
import org.jetbrains.kotlin.codegen.`when`.MappingsClassesForWhenByEnum
@@ -28,6 +30,7 @@ import org.jetbrains.kotlin.codegen.intrinsics.IntrinsicMethods
import org.jetbrains.kotlin.codegen.optimization.OptimizationClassBuilderFactory
import org.jetbrains.kotlin.descriptors.ModuleDescriptor
import org.jetbrains.kotlin.descriptors.ScriptDescriptor
import org.jetbrains.kotlin.diagnostics.Diagnostic
import org.jetbrains.kotlin.diagnostics.DiagnosticSink
import org.jetbrains.kotlin.load.kotlin.incremental.components.IncrementalCompilationComponents
import org.jetbrains.kotlin.modules.TargetId
@@ -96,7 +99,10 @@ public class GenerationState @JvmOverloads constructor(
private var used = false
public val diagnostics: DiagnosticSink get() = extraJvmDiagnosticsTrace
public val collectedExtraJvmDiagnostics: Diagnostics get() = extraJvmDiagnosticsTrace.bindingContext.diagnostics
public val collectedExtraJvmDiagnostics: Diagnostics = LazyJvmDiagnostics {
duplicateSignatureFactory.reportDiagnostics()
extraJvmDiagnosticsTrace.bindingContext.diagnostics
}
public val moduleName: String = moduleName ?: JvmCodegenUtil.getModuleName(module)
public val classBuilderMode: ClassBuilderMode = builderFactory.getClassBuilderMode()
@@ -110,6 +116,7 @@ public class GenerationState @JvmOverloads constructor(
public val reflectionTypes: ReflectionTypes = ReflectionTypes(module)
public val jvmRuntimeTypes: JvmRuntimeTypes = JvmRuntimeTypes()
public val factory: ClassFileFactory
private val duplicateSignatureFactory: BuilderFactoryForDuplicateSignatureDiagnostics
public val replSpecific = ForRepl()
@@ -135,12 +142,13 @@ public class GenerationState @JvmOverloads constructor(
init {
val optimizationClassBuilderFactory = OptimizationClassBuilderFactory(builderFactory, disableOptimization)
var interceptedBuilderFactory: ClassBuilderFactory = BuilderFactoryForDuplicateSignatureDiagnostics(
duplicateSignatureFactory = BuilderFactoryForDuplicateSignatureDiagnostics(
optimizationClassBuilderFactory, this.bindingContext, diagnostics, fileClassesProvider,
getIncrementalCacheForThisTarget(),
this.moduleName)
interceptedBuilderFactory = BuilderFactoryForDuplicateClassNameDiagnostics(interceptedBuilderFactory, diagnostics);
var interceptedBuilderFactory: ClassBuilderFactory
= BuilderFactoryForDuplicateClassNameDiagnostics(duplicateSignatureFactory, diagnostics)
val interceptExtensions = ClassBuilderInterceptorExtension.getInstances(project)
@@ -168,3 +176,20 @@ public class GenerationState @JvmOverloads constructor(
interceptedBuilderFactory.close()
}
}
private class LazyJvmDiagnostics(compute: () -> Diagnostics): Diagnostics {
private val delegate by lazy(LazyThreadSafetyMode.SYNCHRONIZED, compute)
override val modificationTracker: ModificationTracker
get() = delegate.modificationTracker
override fun all(): Collection<Diagnostic> = delegate.all()
override fun forElement(psiElement: PsiElement) = delegate.forElement(psiElement)
override fun isEmpty() = delegate.isEmpty()
override fun noSuppression() = delegate.noSuppression()
override fun iterator() = delegate.iterator()
}