diff --git a/compiler/tests-common/tests/org/jetbrains/kotlin/codegen/GenerationUtils.kt b/compiler/tests-common/tests/org/jetbrains/kotlin/codegen/GenerationUtils.kt index 580f6c1ec19..8c61d9618ae 100644 --- a/compiler/tests-common/tests/org/jetbrains/kotlin/codegen/GenerationUtils.kt +++ b/compiler/tests-common/tests/org/jetbrains/kotlin/codegen/GenerationUtils.kt @@ -17,11 +17,11 @@ package org.jetbrains.kotlin.codegen import com.intellij.openapi.extensions.Extensions +import com.intellij.openapi.project.Project import com.intellij.psi.PsiElementFinder import com.intellij.psi.search.GlobalSearchScope import com.intellij.psi.search.ProjectScope import org.jetbrains.kotlin.TestsCompiletimeError -import org.jetbrains.kotlin.analyzer.ModuleInfo import org.jetbrains.kotlin.asJava.finder.JavaElementFinder import org.jetbrains.kotlin.backend.common.phaser.PhaseConfig import org.jetbrains.kotlin.backend.jvm.JvmIrCodegenFactory @@ -36,25 +36,16 @@ import org.jetbrains.kotlin.config.CommonConfigurationKeys import org.jetbrains.kotlin.config.CompilerConfiguration import org.jetbrains.kotlin.config.JVMConfigurationKeys import org.jetbrains.kotlin.config.languageVersionSettings -import org.jetbrains.kotlin.fir.createSession -import org.jetbrains.kotlin.fir.FirSession import org.jetbrains.kotlin.fir.backend.Fir2IrConverter import org.jetbrains.kotlin.fir.builder.RawFirBuilder -import org.jetbrains.kotlin.fir.java.FirJavaModuleBasedSession -import org.jetbrains.kotlin.fir.java.FirLibrarySession -import org.jetbrains.kotlin.fir.java.FirProjectSessionProvider +import org.jetbrains.kotlin.fir.createSession import org.jetbrains.kotlin.fir.resolve.firProvider import org.jetbrains.kotlin.fir.resolve.impl.FirProviderImpl import org.jetbrains.kotlin.fir.resolve.transformers.FirTotalResolveTransformer import org.jetbrains.kotlin.load.kotlin.PackagePartProvider -import org.jetbrains.kotlin.name.Name -import org.jetbrains.kotlin.platform.TargetPlatform -import org.jetbrains.kotlin.platform.jvm.JvmPlatforms import org.jetbrains.kotlin.psi.KtFile import org.jetbrains.kotlin.resolve.AnalyzingUtils import org.jetbrains.kotlin.resolve.BindingTrace -import org.jetbrains.kotlin.resolve.PlatformDependentAnalyzerServices -import org.jetbrains.kotlin.resolve.jvm.platform.JvmPlatformAnalyzerServices import org.jetbrains.kotlin.resolve.lazy.JvmResolveUtil import java.io.File @@ -90,67 +81,9 @@ object GenerationUtils { ): GenerationState { val project = files.first().project val state = if (configuration.getBoolean(CommonConfigurationKeys.USE_FIR)) { - Extensions.getArea(project) - .getExtensionPoint(PsiElementFinder.EP_NAME) - .unregisterExtension(JavaElementFinder::class.java) - - val scope = GlobalSearchScope.filesScope(project, files.map { it.virtualFile }) - .uniteWith(TopDownAnalyzerFacadeForJVM.AllJavaSourcesInProjectScope(project)) - val librariesScope = ProjectScope.getLibrariesScope(project) - val session = createSession(project, scope, librariesScope, packagePartProvider) - - val builder = RawFirBuilder(session, stubMode = false) - val resolveTransformer = FirTotalResolveTransformer() - val firFiles = files.map { - val firFile = builder.buildFirFile(it) - (session.firProvider as FirProviderImpl).recordFile(firFile) - firFile - }.also { - try { - resolveTransformer.processFiles(it) - } catch (e: Exception) { - throw e - } - } - val (moduleFragment, symbolTable, sourceManager) = - Fir2IrConverter.createModuleFragment(session, firFiles, configuration.languageVersionSettings) - val dummyBindingContext = NoScopeRecordCliBindingTrace().bindingContext - - val codegenFactory = JvmIrCodegenFactory(configuration.get(CLIConfigurationKeys.PHASE_CONFIG) ?: PhaseConfig(jvmPhases)) - val generationState = GenerationState.Builder( - project, classBuilderFactory, moduleFragment.descriptor, dummyBindingContext, files, configuration - ).codegenFactory( - codegenFactory - ).isIrBackend( - true - ).build() - - generationState.beforeCompile() - codegenFactory.generateModuleInFrontendIRMode( - generationState, moduleFragment, CompilationErrorHandler.THROW_EXCEPTION, symbolTable, sourceManager - ) - generationState.factory.done() - generationState + compileFilesUsingFrontendIR(project, files, configuration, classBuilderFactory, packagePartProvider) } else { - val analysisResult = - JvmResolveUtil.analyzeAndCheckForErrors(project, files, configuration, packagePartProvider, trace) - analysisResult.throwIfError() - - /* Currently Kapt3 only works with the old JVM backend, so disable IR for everything except actual bytecode generation. */ - val isIrBackend = - classBuilderFactory.classBuilderMode == ClassBuilderMode.FULL && configuration.getBoolean(JVMConfigurationKeys.IR) - val state = GenerationState.Builder( - project, classBuilderFactory, analysisResult.moduleDescriptor, analysisResult.bindingContext, - files, configuration - ).codegenFactory( - if (isIrBackend) - JvmIrCodegenFactory(configuration.get(CLIConfigurationKeys.PHASE_CONFIG) ?: PhaseConfig(jvmPhases)) - else DefaultCodegenFactory - ).isIrBackend(isIrBackend).build() - if (analysisResult.shouldGenerateCode) { - KotlinCodegenFacade.compileCorrectFiles(state, CompilationErrorHandler.THROW_EXCEPTION) - } - state + compileFilesUsingStandardMode(project, files, configuration, classBuilderFactory, packagePartProvider, trace) } // For JVM-specific errors @@ -162,4 +95,83 @@ object GenerationUtils { return state } -} + + private fun compileFilesUsingFrontendIR( + project: Project, + files: List, + configuration: CompilerConfiguration, + classBuilderFactory: ClassBuilderFactory, + packagePartProvider: (GlobalSearchScope) -> PackagePartProvider + ): GenerationState { + Extensions.getArea(project) + .getExtensionPoint(PsiElementFinder.EP_NAME) + .unregisterExtension(JavaElementFinder::class.java) + + val scope = GlobalSearchScope.filesScope(project, files.map { it.virtualFile }) + .uniteWith(TopDownAnalyzerFacadeForJVM.AllJavaSourcesInProjectScope(project)) + val librariesScope = ProjectScope.getLibrariesScope(project) + val session = createSession(project, scope, librariesScope, packagePartProvider) + + val builder = RawFirBuilder(session, stubMode = false) + val resolveTransformer = FirTotalResolveTransformer() + val firFiles = files.map { + val firFile = builder.buildFirFile(it) + (session.firProvider as FirProviderImpl).recordFile(firFile) + firFile + }.also { + try { + resolveTransformer.processFiles(it) + } catch (e: Exception) { + throw e + } + } + val (moduleFragment, symbolTable, sourceManager) = + Fir2IrConverter.createModuleFragment(session, firFiles, configuration.languageVersionSettings) + val dummyBindingContext = NoScopeRecordCliBindingTrace().bindingContext + + val codegenFactory = JvmIrCodegenFactory(configuration.get(CLIConfigurationKeys.PHASE_CONFIG) ?: PhaseConfig(jvmPhases)) + val generationState = GenerationState.Builder( + project, classBuilderFactory, moduleFragment.descriptor, dummyBindingContext, files, configuration + ).codegenFactory( + codegenFactory + ).isIrBackend( + true + ).build() + + generationState.beforeCompile() + codegenFactory.generateModuleInFrontendIRMode( + generationState, moduleFragment, CompilationErrorHandler.THROW_EXCEPTION, symbolTable, sourceManager + ) + generationState.factory.done() + return generationState + } + + private fun compileFilesUsingStandardMode( + project: Project, + files: List, + configuration: CompilerConfiguration, + classBuilderFactory: ClassBuilderFactory, + packagePartProvider: (GlobalSearchScope) -> PackagePartProvider, + trace: BindingTrace + ): GenerationState { + val analysisResult = + JvmResolveUtil.analyzeAndCheckForErrors(project, files, configuration, packagePartProvider, trace) + analysisResult.throwIfError() + + /* Currently Kapt3 only works with the old JVM backend, so disable IR for everything except actual bytecode generation. */ + val isIrBackend = + classBuilderFactory.classBuilderMode == ClassBuilderMode.FULL && configuration.getBoolean(JVMConfigurationKeys.IR) + val generationState = GenerationState.Builder( + project, classBuilderFactory, analysisResult.moduleDescriptor, analysisResult.bindingContext, + files, configuration + ).codegenFactory( + if (isIrBackend) + JvmIrCodegenFactory(configuration.get(CLIConfigurationKeys.PHASE_CONFIG) ?: PhaseConfig(jvmPhases)) + else DefaultCodegenFactory + ).isIrBackend(isIrBackend).build() + if (analysisResult.shouldGenerateCode) { + KotlinCodegenFacade.compileCorrectFiles(generationState, CompilationErrorHandler.THROW_EXCEPTION) + } + return generationState + } +} \ No newline at end of file