[FIR] do not use FirValueParameter for function type parameter As it is a different abstraction, introduced FirFunctionTypeParameter instead Also, fix syntax checkers for function type parameter ^KT-55035 fixed
diff --git a/analysis/analysis-api-fir/src/org/jetbrains/kotlin/analysis/api/fir/components/KtFirExpressionTypeProvider.kt b/analysis/analysis-api-fir/src/org/jetbrains/kotlin/analysis/api/fir/components/KtFirExpressionTypeProvider.kt index b74b7d1..af54411 100644 --- a/analysis/analysis-api-fir/src/org/jetbrains/kotlin/analysis/api/fir/components/KtFirExpressionTypeProvider.kt +++ b/analysis/analysis-api-fir/src/org/jetbrains/kotlin/analysis/api/fir/components/KtFirExpressionTypeProvider.kt
@@ -15,12 +15,11 @@ import org.jetbrains.kotlin.analysis.low.level.api.fir.api.getOrBuildFir import org.jetbrains.kotlin.analysis.low.level.api.fir.api.getOrBuildFirOfType import org.jetbrains.kotlin.analysis.low.level.api.fir.api.getOrBuildFirSafe -import org.jetbrains.kotlin.fir.FirLabel -import org.jetbrains.kotlin.fir.FirPackageDirective +import org.jetbrains.kotlin.analysis.utils.errors.unexpectedElementError +import org.jetbrains.kotlin.fir.* import org.jetbrains.kotlin.fir.declarations.* import org.jetbrains.kotlin.fir.declarations.utils.isSuspend import org.jetbrains.kotlin.fir.expressions.* -import org.jetbrains.kotlin.fir.psi import org.jetbrains.kotlin.fir.references.FirNamedReference import org.jetbrains.kotlin.fir.references.FirResolvedNamedReference import org.jetbrains.kotlin.fir.references.FirSuperReference @@ -99,8 +98,12 @@ val firDeclaration = if (isAnonymousFunction(declaration)) declaration.toFirAnonymousFunction() else - declaration.getOrBuildFirOfType<FirCallableDeclaration>(firResolveSession) - return firDeclaration.returnTypeRef.coneType.asKtType() + declaration.getOrBuildFir(firResolveSession) + return when (firDeclaration) { + is FirCallableDeclaration -> firDeclaration.returnTypeRef.coneType.asKtType() + is FirFunctionTypeParameter -> firDeclaration.returnTypeRef.coneType.asKtType() + else -> unexpectedElementError<FirElement>(firDeclaration) + } } override fun getFunctionalTypeForKtFunction(declaration: KtFunction): KtType {
diff --git a/analysis/low-level-api-fir/src/org/jetbrains/kotlin/analysis/low/level/api/fir/api/KtDeclarationAndFirDeclarationEqualityChecker.kt b/analysis/low-level-api-fir/src/org/jetbrains/kotlin/analysis/low/level/api/fir/api/KtDeclarationAndFirDeclarationEqualityChecker.kt index 768c16f..03de7b0 100644 --- a/analysis/low-level-api-fir/src/org/jetbrains/kotlin/analysis/low/level/api/fir/api/KtDeclarationAndFirDeclarationEqualityChecker.kt +++ b/analysis/low-level-api-fir/src/org/jetbrains/kotlin/analysis/low/level/api/fir/api/KtDeclarationAndFirDeclarationEqualityChecker.kt
@@ -121,7 +121,7 @@ append(classId.asSingleFqName().toString()) val parameters = buildList { receiverTypeRef?.let(::add) - valueParameters.mapTo(this) { it.returnTypeRef } + parameters.mapTo(this) { it.returnTypeRef } returnTypeRef.let(::add) } if (parameters.isNotEmpty()) {
diff --git a/analysis/low-level-api-fir/testdata/getOrBuildFir/types/functionalTypeArgument.txt b/analysis/low-level-api-fir/testdata/getOrBuildFir/types/functionalTypeArgument.txt index 0130de8..17750fb 100644 --- a/analysis/low-level-api-fir/testdata/getOrBuildFir/types/functionalTypeArgument.txt +++ b/analysis/low-level-api-fir/testdata/getOrBuildFir/types/functionalTypeArgument.txt
@@ -1,6 +1,6 @@ KT element: KtParameter -FIR element: FirValueParameterImpl +FIR element: FirFunctionTypeParameterImpl FIR source kind: KtRealSourceElementKind FIR element rendered: -R|kotlin/Int| +R|kotlin/Int| \ No newline at end of file
diff --git a/compiler/fir/checkers/checkers.jvm/src/org/jetbrains/kotlin/fir/analysis/jvm/FirJvmNamesChecker.kt b/compiler/fir/checkers/checkers.jvm/src/org/jetbrains/kotlin/fir/analysis/jvm/FirJvmNamesChecker.kt new file mode 100644 index 0000000..dfac804 --- /dev/null +++ b/compiler/fir/checkers/checkers.jvm/src/org/jetbrains/kotlin/fir/analysis/jvm/FirJvmNamesChecker.kt
@@ -0,0 +1,48 @@ +/* + * Copyright 2010-2022 JetBrains s.r.o. and Kotlin Programming Language contributors. + * Use of this source code is governed by the Apache 2.0 license that can be found in the license/LICENSE.txt file. + */ + +package org.jetbrains.kotlin.fir.analysis.jvm + +import org.jetbrains.kotlin.KtFakeSourceElementKind +import org.jetbrains.kotlin.KtSourceElement +import org.jetbrains.kotlin.diagnostics.DiagnosticReporter +import org.jetbrains.kotlin.diagnostics.reportOn +import org.jetbrains.kotlin.fir.analysis.checkers.context.CheckerContext +import org.jetbrains.kotlin.fir.analysis.diagnostics.FirErrors +import org.jetbrains.kotlin.name.Name + +object FirJvmNamesChecker { + // See The Java Virtual Machine Specification, section 4.7.9.1 https://docs.oracle.com/javase/specs/jvms/se8/html/jvms-4.html#jvms-4.7.9.1 + private val INVALID_CHARS = setOf('.', ';', '[', ']', '/', '<', '>', ':', '\\') + + // These characters can cause problems on Windows. '?*"|' are not allowed in file names, and % leads to unexpected env var expansion. + private val DANGEROUS_CHARS = setOf('?', '*', '"', '|', '%') + + + fun checkNameAndReport(name: Name, declarationSource: KtSourceElement?, context: CheckerContext, reporter: DiagnosticReporter) { + if (declarationSource != null && + declarationSource.kind !is KtFakeSourceElementKind && + !name.isSpecial + ) { + val nameString = name.asString() + if (nameString.any { it in INVALID_CHARS }) { + reporter.reportOn( + declarationSource, + FirErrors.INVALID_CHARACTERS, + "contains illegal characters: ${INVALID_CHARS.intersect(nameString.toSet()).joinToString("")}", + context + ) + } else if (nameString.any { it in DANGEROUS_CHARS }) { + reporter.reportOn( + declarationSource, + FirErrors.DANGEROUS_CHARACTERS, + DANGEROUS_CHARS.intersect(nameString.toSet()).joinToString(""), + context + ) + } + } + + } +} \ No newline at end of file
diff --git a/compiler/fir/checkers/checkers.jvm/src/org/jetbrains/kotlin/fir/analysis/jvm/checkers/JvmTypeCheckers.kt b/compiler/fir/checkers/checkers.jvm/src/org/jetbrains/kotlin/fir/analysis/jvm/checkers/JvmTypeCheckers.kt index 37e9daf..040490d 100644 --- a/compiler/fir/checkers/checkers.jvm/src/org/jetbrains/kotlin/fir/analysis/jvm/checkers/JvmTypeCheckers.kt +++ b/compiler/fir/checkers/checkers.jvm/src/org/jetbrains/kotlin/fir/analysis/jvm/checkers/JvmTypeCheckers.kt
@@ -7,9 +7,11 @@ import org.jetbrains.kotlin.fir.analysis.checkers.declaration.FirDynamicUnsupportedChecker import org.jetbrains.kotlin.fir.analysis.checkers.type.* +import org.jetbrains.kotlin.fir.analysis.jvm.checkers.type.FirFunctionalTypeParameterNameChecker object JvmTypeCheckers : TypeCheckers() { override val typeRefCheckers: Set<FirTypeRefChecker> = setOf( FirDynamicUnsupportedChecker, + FirFunctionalTypeParameterNameChecker, ) }
diff --git a/compiler/fir/checkers/checkers.jvm/src/org/jetbrains/kotlin/fir/analysis/jvm/checkers/declaration/FirJvmInvalidAndDangerousCharactersChecker.kt b/compiler/fir/checkers/checkers.jvm/src/org/jetbrains/kotlin/fir/analysis/jvm/checkers/declaration/FirJvmInvalidAndDangerousCharactersChecker.kt index 5f467c1..a612354 100644 --- a/compiler/fir/checkers/checkers.jvm/src/org/jetbrains/kotlin/fir/analysis/jvm/checkers/declaration/FirJvmInvalidAndDangerousCharactersChecker.kt +++ b/compiler/fir/checkers/checkers.jvm/src/org/jetbrains/kotlin/fir/analysis/jvm/checkers/declaration/FirJvmInvalidAndDangerousCharactersChecker.kt
@@ -5,57 +5,23 @@ package org.jetbrains.kotlin.fir.analysis.jvm.checkers.declaration -import org.jetbrains.kotlin.KtFakeSourceElementKind -import org.jetbrains.kotlin.KtSourceElement -import org.jetbrains.kotlin.fir.analysis.checkers.context.CheckerContext import org.jetbrains.kotlin.diagnostics.DiagnosticReporter -import org.jetbrains.kotlin.fir.analysis.diagnostics.FirErrors -import org.jetbrains.kotlin.diagnostics.reportOn +import org.jetbrains.kotlin.fir.analysis.checkers.context.CheckerContext import org.jetbrains.kotlin.fir.analysis.checkers.declaration.FirBasicDeclarationChecker +import org.jetbrains.kotlin.fir.analysis.jvm.FirJvmNamesChecker import org.jetbrains.kotlin.fir.declarations.* -import org.jetbrains.kotlin.name.Name object FirJvmInvalidAndDangerousCharactersChecker : FirBasicDeclarationChecker() { - // See The Java Virtual Machine Specification, section 4.7.9.1 https://docs.oracle.com/javase/specs/jvms/se8/html/jvms-4.html#jvms-4.7.9.1 - private val INVALID_CHARS = setOf('.', ';', '[', ']', '/', '<', '>', ':', '\\') - - // These characters can cause problems on Windows. '?*"|' are not allowed in file names, and % leads to unexpected env var expansion. - private val DANGEROUS_CHARS = setOf('?', '*', '"', '|', '%') - override fun check(declaration: FirDeclaration, context: CheckerContext, reporter: DiagnosticReporter) { val source = declaration.source when (declaration) { - is FirRegularClass -> checkNameAndReport(declaration.name, source, context, reporter) - is FirSimpleFunction -> checkNameAndReport(declaration.name, source, context, reporter) - is FirTypeParameter -> checkNameAndReport(declaration.name, source, context, reporter) - is FirProperty -> checkNameAndReport(declaration.name, source, context, reporter) - is FirTypeAlias -> checkNameAndReport(declaration.name, source, context, reporter) - is FirValueParameter -> checkNameAndReport(declaration.name, source, context, reporter) + is FirRegularClass -> FirJvmNamesChecker.checkNameAndReport(declaration.name, source, context, reporter) + is FirSimpleFunction -> FirJvmNamesChecker.checkNameAndReport(declaration.name, source, context, reporter) + is FirTypeParameter -> FirJvmNamesChecker.checkNameAndReport(declaration.name, source, context, reporter) + is FirProperty -> FirJvmNamesChecker.checkNameAndReport(declaration.name, source, context, reporter) + is FirTypeAlias -> FirJvmNamesChecker.checkNameAndReport(declaration.name, source, context, reporter) + is FirValueParameter -> FirJvmNamesChecker.checkNameAndReport(declaration.name, source, context, reporter) else -> return } } - - private fun checkNameAndReport(name: Name, source: KtSourceElement?, context: CheckerContext, reporter: DiagnosticReporter) { - if (source != null && - source.kind !is KtFakeSourceElementKind && - !name.isSpecial - ) { - val nameString = name.asString() - if (nameString.any { it in INVALID_CHARS }) { - reporter.reportOn( - source, - FirErrors.INVALID_CHARACTERS, - "contains illegal characters: ${INVALID_CHARS.intersect(nameString.toSet()).joinToString("")}", - context - ) - } else if (nameString.any { it in DANGEROUS_CHARS }) { - reporter.reportOn( - source, - FirErrors.DANGEROUS_CHARACTERS, - DANGEROUS_CHARS.intersect(nameString.toSet()).joinToString(""), - context - ) - } - } - } } \ No newline at end of file
diff --git a/compiler/fir/checkers/checkers.jvm/src/org/jetbrains/kotlin/fir/analysis/jvm/checkers/type/FirFunctionalTypeParameterNameChecker.kt b/compiler/fir/checkers/checkers.jvm/src/org/jetbrains/kotlin/fir/analysis/jvm/checkers/type/FirFunctionalTypeParameterNameChecker.kt new file mode 100644 index 0000000..02a2be7 --- /dev/null +++ b/compiler/fir/checkers/checkers.jvm/src/org/jetbrains/kotlin/fir/analysis/jvm/checkers/type/FirFunctionalTypeParameterNameChecker.kt
@@ -0,0 +1,29 @@ +/* + * Copyright 2010-2022 JetBrains s.r.o. and Kotlin Programming Language contributors. + * Use of this source code is governed by the Apache 2.0 license that can be found in the license/LICENSE.txt file. + */ + +package org.jetbrains.kotlin.fir.analysis.jvm.checkers.type + +import org.jetbrains.kotlin.diagnostics.DiagnosticReporter +import org.jetbrains.kotlin.fir.FirFunctionTypeParameter +import org.jetbrains.kotlin.fir.analysis.checkers.context.CheckerContext +import org.jetbrains.kotlin.fir.analysis.checkers.type.FirTypeRefChecker +import org.jetbrains.kotlin.fir.analysis.jvm.FirJvmNamesChecker +import org.jetbrains.kotlin.fir.types.FirFunctionTypeRef +import org.jetbrains.kotlin.fir.types.FirTypeRef + +object FirFunctionalTypeParameterNameChecker : FirTypeRefChecker() { + override fun check(typeRef: FirTypeRef, context: CheckerContext, reporter: DiagnosticReporter) { + if (typeRef !is FirFunctionTypeRef) return + for (parameter in typeRef.parameters) { + check(parameter, context, reporter) + } + } + + private fun check(typeRef: FirFunctionTypeParameter, context: CheckerContext, reporter: DiagnosticReporter) { + val name = typeRef.name ?: return + val typeRefSource = typeRef.source ?: return + FirJvmNamesChecker.checkNameAndReport(name, typeRefSource, context, reporter) + } +} \ No newline at end of file
diff --git a/compiler/fir/checkers/src/org/jetbrains/kotlin/fir/analysis/checkers/CommonDeclarationCheckers.kt b/compiler/fir/checkers/src/org/jetbrains/kotlin/fir/analysis/checkers/CommonDeclarationCheckers.kt index e89a46b..b12ccaf 100644 --- a/compiler/fir/checkers/src/org/jetbrains/kotlin/fir/analysis/checkers/CommonDeclarationCheckers.kt +++ b/compiler/fir/checkers/src/org/jetbrains/kotlin/fir/analysis/checkers/CommonDeclarationCheckers.kt
@@ -165,7 +165,5 @@ ) override val valueParameterCheckers: Set<FirValueParameterChecker> - get() = setOf( - FirUnsupportedDefaultValueInFunctionTypeChecker - ) + get() = setOf() }
diff --git a/compiler/fir/checkers/src/org/jetbrains/kotlin/fir/analysis/checkers/CommonTypeCheckers.kt b/compiler/fir/checkers/src/org/jetbrains/kotlin/fir/analysis/checkers/CommonTypeCheckers.kt index 899b286..36a9296 100644 --- a/compiler/fir/checkers/src/org/jetbrains/kotlin/fir/analysis/checkers/CommonTypeCheckers.kt +++ b/compiler/fir/checkers/src/org/jetbrains/kotlin/fir/analysis/checkers/CommonTypeCheckers.kt
@@ -5,6 +5,7 @@ package org.jetbrains.kotlin.fir.analysis.checkers +import org.jetbrains.kotlin.fir.analysis.checkers.type.FirUnsupportedDefaultValueInFunctionTypeParameterChecker import org.jetbrains.kotlin.fir.analysis.checkers.type.* object CommonTypeCheckers : TypeCheckers() { @@ -14,5 +15,7 @@ FirDeprecatedTypeChecker, FirOptInUsageTypeRefChecker, FirDefinitelyNotNullableChecker, + FirUnsupportedDefaultValueInFunctionTypeParameterChecker, + FirUnsupportedModifiersInFunctionTypeParameterChecker, ) }
diff --git a/compiler/fir/checkers/src/org/jetbrains/kotlin/fir/analysis/checkers/FirHelpers.kt b/compiler/fir/checkers/src/org/jetbrains/kotlin/fir/analysis/checkers/FirHelpers.kt index 3f73771..41705d6 100644 --- a/compiler/fir/checkers/src/org/jetbrains/kotlin/fir/analysis/checkers/FirHelpers.kt +++ b/compiler/fir/checkers/src/org/jetbrains/kotlin/fir/analysis/checkers/FirHelpers.kt
@@ -5,8 +5,9 @@ package org.jetbrains.kotlin.fir.analysis.checkers -import org.jetbrains.kotlin.KtFakeSourceElementKind -import org.jetbrains.kotlin.KtSourceElement +import com.intellij.lang.LighterASTNode +import com.intellij.openapi.util.Ref +import org.jetbrains.kotlin.* import org.jetbrains.kotlin.builtins.StandardNames.HASHCODE_NAME import org.jetbrains.kotlin.descriptors.ClassKind import org.jetbrains.kotlin.descriptors.Modality @@ -17,8 +18,8 @@ import org.jetbrains.kotlin.fir.analysis.checkers.context.CheckerContext import org.jetbrains.kotlin.fir.analysis.diagnostics.FirErrors import org.jetbrains.kotlin.fir.analysis.getChild -import org.jetbrains.kotlin.fir.containingClassLookupTag import org.jetbrains.kotlin.fir.containingClassForLocalAttr +import org.jetbrains.kotlin.fir.containingClassLookupTag import org.jetbrains.kotlin.fir.declarations.* import org.jetbrains.kotlin.fir.declarations.utils.* import org.jetbrains.kotlin.fir.expressions.* @@ -41,6 +42,7 @@ import org.jetbrains.kotlin.fir.unwrapFakeOverrides import org.jetbrains.kotlin.lexer.KtTokens import org.jetbrains.kotlin.name.* +import org.jetbrains.kotlin.psi.KtParameter import org.jetbrains.kotlin.psi.KtParameter.VAL_VAR_TOKEN_SET import org.jetbrains.kotlin.resolve.AnnotationTargetList import org.jetbrains.kotlin.resolve.AnnotationTargetLists @@ -537,10 +539,10 @@ } } is FirFunctionTypeRef -> { - val valueParameters = delegatedTypeRef.valueParameters + val parameters = delegatedTypeRef.parameters delegatedTypeRef.receiverTypeRef?.let { result.add(FirTypeRefSource(it, it.source)) } - for (valueParameter in valueParameters) { + for (valueParameter in parameters) { val valueParamTypeRef = valueParameter.returnTypeRef result.add(FirTypeRefSource(valueParamTypeRef, valueParamTypeRef.source)) } @@ -669,3 +671,36 @@ fun FirQualifiedAccess.explicitReceiverIsNotSuperReference(): Boolean { return (this.explicitReceiver as? FirQualifiedAccessExpression)?.calleeReference !is FirSuperReference } + + +internal val KtSourceElement.defaultValueForParameter: KtSourceElement? + get() = when (this) { + is KtPsiSourceElement -> (psi as? KtParameter)?.defaultValue?.toKtPsiSourceElement() + is KtLightSourceElement -> findDefaultValue(this) + } + +private fun findDefaultValue(source: KtLightSourceElement): KtLightSourceElement? { + val childrenRef = Ref<Array<LighterASTNode?>>() + source.treeStructure.getChildren(source.lighterASTNode, childrenRef) + + var defaultValue: LighterASTNode? = null + var defaultValueOffset = source.startOffset + + for (node in childrenRef.get()) { + if (node == null) continue + if (node.isExpression()) { + defaultValue = node + break + } else { + defaultValueOffset += node.endOffset - node.startOffset + } + } + if (defaultValue == null) return null + + return defaultValue.toKtLightSourceElement( + source.treeStructure, + startOffset = defaultValueOffset, + endOffset = defaultValueOffset + defaultValue.textLength, + ) +} +
diff --git a/compiler/fir/checkers/src/org/jetbrains/kotlin/fir/analysis/checkers/declaration/FirUnsupportedDefaultValueInFunctionTypeChecker.kt b/compiler/fir/checkers/src/org/jetbrains/kotlin/fir/analysis/checkers/declaration/FirUnsupportedDefaultValueInFunctionTypeChecker.kt deleted file mode 100644 index 4507ee6..0000000 --- a/compiler/fir/checkers/src/org/jetbrains/kotlin/fir/analysis/checkers/declaration/FirUnsupportedDefaultValueInFunctionTypeChecker.kt +++ /dev/null
@@ -1,23 +0,0 @@ -/* - * Copyright 2010-2022 JetBrains s.r.o. and Kotlin Programming Language contributors. - * Use of this source code is governed by the Apache 2.0 license that can be found in the license/LICENSE.txt file. - */ - -package org.jetbrains.kotlin.fir.analysis.checkers.declaration - -import org.jetbrains.kotlin.diagnostics.DiagnosticReporter -import org.jetbrains.kotlin.diagnostics.reportOn -import org.jetbrains.kotlin.fir.analysis.checkers.context.CheckerContext -import org.jetbrains.kotlin.fir.analysis.diagnostics.FirErrors -import org.jetbrains.kotlin.fir.declarations.FirValueParameter -import org.jetbrains.kotlin.fir.resolve.diagnostics.ConeUnsupportedDefaultValueInFunctionType -import org.jetbrains.kotlin.fir.types.FirErrorTypeRef - -object FirUnsupportedDefaultValueInFunctionTypeChecker : FirValueParameterChecker() { - override fun check(declaration: FirValueParameter, context: CheckerContext, reporter: DiagnosticReporter) { - val diagnostic = ((declaration.defaultValue?.typeRef as? FirErrorTypeRef)?.diagnostic as? ConeUnsupportedDefaultValueInFunctionType) - if (diagnostic != null) { - reporter.reportOn(diagnostic.source, FirErrors.UNSUPPORTED, diagnostic.reason, context) - } - } -} \ No newline at end of file
diff --git a/compiler/fir/checkers/src/org/jetbrains/kotlin/fir/analysis/checkers/type/FirFunctionalTypeParameterSyntaxChecker.kt b/compiler/fir/checkers/src/org/jetbrains/kotlin/fir/analysis/checkers/type/FirFunctionalTypeParameterSyntaxChecker.kt new file mode 100644 index 0000000..1553596 --- /dev/null +++ b/compiler/fir/checkers/src/org/jetbrains/kotlin/fir/analysis/checkers/type/FirFunctionalTypeParameterSyntaxChecker.kt
@@ -0,0 +1,23 @@ +/* + * Copyright 2010-2022 JetBrains s.r.o. and Kotlin Programming Language contributors. + * Use of this source code is governed by the Apache 2.0 license that can be found in the license/LICENSE.txt file. + */ + +package org.jetbrains.kotlin.fir.analysis.checkers.type + +import org.jetbrains.kotlin.diagnostics.DiagnosticReporter +import org.jetbrains.kotlin.fir.FirFunctionTypeParameter +import org.jetbrains.kotlin.fir.analysis.checkers.context.CheckerContext +import org.jetbrains.kotlin.fir.analysis.checkers.syntax.FirSyntaxChecker +import org.jetbrains.kotlin.fir.types.FirFunctionTypeRef +import org.jetbrains.kotlin.fir.types.FirTypeRef +import org.jetbrains.kotlin.psi.KtParameter + +abstract class FirFunctionalTypeParameterSyntaxChecker : FirTypeRefChecker(), FirSyntaxChecker<FirFunctionTypeParameter, KtParameter> { + override fun check(typeRef: FirTypeRef, context: CheckerContext, reporter: DiagnosticReporter) { + if (typeRef !is FirFunctionTypeRef) return + for (parameter in typeRef.parameters) { + checkSyntax(parameter, context, reporter) + } + } +} \ No newline at end of file
diff --git a/compiler/fir/checkers/src/org/jetbrains/kotlin/fir/analysis/checkers/type/FirUnsupportedDefaultValueInFunctionTypeParameterChecker.kt b/compiler/fir/checkers/src/org/jetbrains/kotlin/fir/analysis/checkers/type/FirUnsupportedDefaultValueInFunctionTypeParameterChecker.kt new file mode 100644 index 0000000..1e2d453 --- /dev/null +++ b/compiler/fir/checkers/src/org/jetbrains/kotlin/fir/analysis/checkers/type/FirUnsupportedDefaultValueInFunctionTypeParameterChecker.kt
@@ -0,0 +1,32 @@ +/* + * Copyright 2010-2022 JetBrains s.r.o. and Kotlin Programming Language contributors. + * Use of this source code is governed by the Apache 2.0 license that can be found in the license/LICENSE.txt file. + */ + +package org.jetbrains.kotlin.fir.analysis.checkers.type + +import org.jetbrains.kotlin.KtSourceElement +import org.jetbrains.kotlin.diagnostics.DiagnosticReporter +import org.jetbrains.kotlin.diagnostics.reportOn +import org.jetbrains.kotlin.fir.FirFunctionTypeParameter +import org.jetbrains.kotlin.fir.analysis.checkers.context.CheckerContext +import org.jetbrains.kotlin.fir.analysis.checkers.defaultValueForParameter +import org.jetbrains.kotlin.fir.analysis.diagnostics.FirErrors +import org.jetbrains.kotlin.fir.resolve.diagnostics.ConeUnsupportedDefaultValueInFunctionType + +object FirUnsupportedDefaultValueInFunctionTypeParameterChecker : FirFunctionalTypeParameterSyntaxChecker() { + override fun checkPsiOrLightTree( + element: FirFunctionTypeParameter, + source: KtSourceElement, + context: CheckerContext, + reporter: DiagnosticReporter + ) { + val defaultValue = source.defaultValueForParameter ?: return + report(defaultValue, reporter, context) + } + + private fun report(defaultValueSource: KtSourceElement, reporter: DiagnosticReporter, context: CheckerContext) { + val diagnostic = ConeUnsupportedDefaultValueInFunctionType(defaultValueSource) + reporter.reportOn(diagnostic.source, FirErrors.UNSUPPORTED, diagnostic.reason, context) + } +} \ No newline at end of file
diff --git a/compiler/fir/checkers/src/org/jetbrains/kotlin/fir/analysis/checkers/type/FirUnsupportedModifiersInFunctionTypeParameterChecker.kt b/compiler/fir/checkers/src/org/jetbrains/kotlin/fir/analysis/checkers/type/FirUnsupportedModifiersInFunctionTypeParameterChecker.kt new file mode 100644 index 0000000..9dc3cc9 --- /dev/null +++ b/compiler/fir/checkers/src/org/jetbrains/kotlin/fir/analysis/checkers/type/FirUnsupportedModifiersInFunctionTypeParameterChecker.kt
@@ -0,0 +1,64 @@ +/* + * Copyright 2010-2022 JetBrains s.r.o. and Kotlin Programming Language contributors. + * Use of this source code is governed by the Apache 2.0 license that can be found in the license/LICENSE.txt file. + */ + +package org.jetbrains.kotlin.fir.analysis.checkers.type + +import org.jetbrains.kotlin.* +import org.jetbrains.kotlin.diagnostics.DiagnosticReporter +import org.jetbrains.kotlin.diagnostics.reportOn +import org.jetbrains.kotlin.diagnostics.valOrVarKeyword +import org.jetbrains.kotlin.fir.FirFunctionTypeParameter +import org.jetbrains.kotlin.fir.analysis.checkers.context.CheckerContext +import org.jetbrains.kotlin.fir.analysis.checkers.getModifierList +import org.jetbrains.kotlin.fir.analysis.checkers.syntax.FirSyntaxChecker +import org.jetbrains.kotlin.fir.analysis.diagnostics.FirErrors +import org.jetbrains.kotlin.fir.types.FirFunctionTypeRef +import org.jetbrains.kotlin.fir.types.FirTypeRef +import org.jetbrains.kotlin.psi.KtParameter +import org.jetbrains.kotlin.psi.KtValVarKeywordOwner + +object FirUnsupportedModifiersInFunctionTypeParameterChecker : FirFunctionalTypeParameterSyntaxChecker() { + + override fun checkPsiOrLightTree( + element: FirFunctionTypeParameter, + source: KtSourceElement, + context: CheckerContext, + reporter: DiagnosticReporter + ) { + checkModifiers(source, reporter, context) + checkValOrVarKeyword(source, reporter, context) + } + + private fun checkValOrVarKeyword(source: KtSourceElement, reporter: DiagnosticReporter, context: CheckerContext) { + val keyword = when (source) { + is KtPsiSourceElement -> + (source.psi as? KtValVarKeywordOwner)?.valOrVarKeyword?.toKtPsiSourceElement() + + is KtLightSourceElement -> + source.treeStructure.valOrVarKeyword(source.lighterASTNode)?.toKtLightSourceElement(source.treeStructure) + + } ?: return + + reporter.reportOn( + keyword, + FirErrors.UNSUPPORTED, + "val or var on parameter in function type", + context + ) + } + + private fun checkModifiers(source: KtSourceElement, reporter: DiagnosticReporter, context: CheckerContext): Boolean { + val modifiersList = source.getModifierList() ?: return true + for (modifier in modifiersList.modifiers) { + reporter.reportOn( + modifier.source, + FirErrors.UNSUPPORTED, + "modifier on parameter in function type", + context + ) + } + return false + } +} \ No newline at end of file
diff --git a/compiler/fir/providers/src/org/jetbrains/kotlin/fir/resolve/LookupTagUtils.kt b/compiler/fir/providers/src/org/jetbrains/kotlin/fir/resolve/LookupTagUtils.kt index 268fafa..98e305c 100644 --- a/compiler/fir/providers/src/org/jetbrains/kotlin/fir/resolve/LookupTagUtils.kt +++ b/compiler/fir/providers/src/org/jetbrains/kotlin/fir/resolve/LookupTagUtils.kt
@@ -8,9 +8,9 @@ import org.jetbrains.kotlin.KtFakeSourceElementKind import org.jetbrains.kotlin.builtins.StandardNames import org.jetbrains.kotlin.fakeElement +import org.jetbrains.kotlin.fir.FirFunctionTypeParameter import org.jetbrains.kotlin.fir.FirSession import org.jetbrains.kotlin.fir.declarations.FirRegularClass -import org.jetbrains.kotlin.fir.declarations.FirValueParameter import org.jetbrains.kotlin.fir.declarations.getAnnotationsByClassId import org.jetbrains.kotlin.fir.expressions.builder.buildAnnotation import org.jetbrains.kotlin.fir.expressions.builder.buildAnnotationArgumentMapping @@ -76,12 +76,13 @@ return lookupTag.toSymbol(session) } -fun ConeKotlinType.withParameterNameAnnotation(valueParameter: FirValueParameter): ConeKotlinType { - if (valueParameter.name == SpecialNames.NO_NAME_PROVIDED || valueParameter.name == SpecialNames.UNDERSCORE_FOR_UNUSED_VAR) return this +fun ConeKotlinType.withParameterNameAnnotation(parameter: FirFunctionTypeParameter): ConeKotlinType { + val name = parameter.name + if (name == null || name == SpecialNames.NO_NAME_PROVIDED || name == SpecialNames.UNDERSCORE_FOR_UNUSED_VAR) return this // Existing @ParameterName annotation takes precedence if (attributes.customAnnotations.getAnnotationsByClassId(StandardNames.FqNames.parameterNameClassId).isNotEmpty()) return this - val fakeSource = valueParameter.source?.fakeElement(KtFakeSourceElementKind.ParameterNameAnnotationCall) + val fakeSource = parameter.source?.fakeElement(KtFakeSourceElementKind.ParameterNameAnnotationCall) val parameterNameAnnotationCall = buildAnnotation { source = fakeSource annotationTypeRef = @@ -95,7 +96,7 @@ } argumentMapping = buildAnnotationArgumentMapping { mapping[StandardClassIds.Annotations.ParameterNames.parameterNameName] = - buildConstExpression(fakeSource, ConstantValueKind.String, valueParameter.name.asString(), setType = true) + buildConstExpression(fakeSource, ConstantValueKind.String, name.asString(), setType = true) } } val attributesWithParameterNameAnnotation =
diff --git a/compiler/fir/raw-fir/light-tree2fir/src/org/jetbrains/kotlin/fir/lightTree/converter/DeclarationsConverter.kt b/compiler/fir/raw-fir/light-tree2fir/src/org/jetbrains/kotlin/fir/lightTree/converter/DeclarationsConverter.kt index 4d03654..84906d0 100644 --- a/compiler/fir/raw-fir/light-tree2fir/src/org/jetbrains/kotlin/fir/lightTree/converter/DeclarationsConverter.kt +++ b/compiler/fir/raw-fir/light-tree2fir/src/org/jetbrains/kotlin/fir/lightTree/converter/DeclarationsConverter.kt
@@ -2170,11 +2170,11 @@ ): FirTypeRef { var receiverTypeReference: FirTypeRef? = null lateinit var returnTypeReference: FirTypeRef - val valueParametersList = mutableListOf<ValueParameter>() + val parameters = mutableListOf<FirFunctionTypeParameter>() functionType.forEachChildren { when (it.tokenType) { FUNCTION_TYPE_RECEIVER -> receiverTypeReference = convertReceiverType(it) - VALUE_PARAMETER_LIST -> valueParametersList += convertValueParameters(it, ValueParameterDeclaration.FUNCTIONAL_TYPE) + VALUE_PARAMETER_LIST -> parameters += convertFunctionTypeParameters(it) TYPE_REFERENCE -> returnTypeReference = convertType(it) } } @@ -2184,7 +2184,7 @@ isMarkedNullable = isNullable receiverTypeRef = receiverTypeReference returnTypeRef = returnTypeReference - valueParameters += valueParametersList.map { it.firValueParameter } + this.parameters += parameters this.isSuspend = isSuspend this.contextReceiverTypeRefs.addAll( functionType.getChildNodeByType(CONTEXT_RECEIVER_LIST)?.getChildNodesByType(CONTEXT_RECEIVER)?.mapNotNull { @@ -2194,6 +2194,30 @@ } } + private fun convertFunctionTypeParameters( + parameters: LighterASTNode, + ): List<FirFunctionTypeParameter> { + return parameters.forEachChildrenReturnList { node, container -> + when (node.tokenType) { + VALUE_PARAMETER -> { + var name: Name? = null + var typeRef: FirTypeRef? = null + node.forEachChildren { + when (it.tokenType) { + IDENTIFIER -> name = it.asText.nameAsSafeName() + TYPE_REFERENCE -> typeRef = convertType(it) + } + } + container += buildFunctionTypeParameter { + source = node.toFirSourceElement() + this.name = name + this.returnTypeRef = typeRef ?: createNoTypeForParameterTypeRef() + } + } + } + } + } + /** * @see org.jetbrains.kotlin.parsing.KotlinParsing.parseValueParameterList */
diff --git a/compiler/fir/raw-fir/psi2fir/src/org/jetbrains/kotlin/fir/builder/RawFirBuilder.kt b/compiler/fir/raw-fir/psi2fir/src/org/jetbrains/kotlin/fir/builder/RawFirBuilder.kt index 4e8149c..8ca72ef 100644 --- a/compiler/fir/raw-fir/psi2fir/src/org/jetbrains/kotlin/fir/builder/RawFirBuilder.kt +++ b/compiler/fir/raw-fir/psi2fir/src/org/jetbrains/kotlin/fir/builder/RawFirBuilder.kt
@@ -1815,7 +1815,14 @@ // TODO: probably implicit type should not be here returnTypeRef = unwrappedElement.returnTypeReference.toFirOrErrorType() for (valueParameter in unwrappedElement.parameters) { - valueParameters += convertValueParameter(valueParameter, valueParameterDeclaration = ValueParameterDeclaration.FUNCTIONAL_TYPE) + parameters += buildFunctionTypeParameter { + this.source = valueParameter.toFirSourceElement() + name = valueParameter.nameAsName + returnTypeRef = when { + valueParameter.typeReference != null -> valueParameter.typeReference.toFirOrErrorType() + else -> createNoTypeForParameterTypeRef() + } + } } contextReceiverTypeRefs.addAll(
diff --git a/compiler/fir/raw-fir/psi2fir/tests/org/jetbrains/kotlin/fir/builder/AbstractRawFirBuilderTestCase.kt b/compiler/fir/raw-fir/psi2fir/tests/org/jetbrains/kotlin/fir/builder/AbstractRawFirBuilderTestCase.kt index aca2ac2..bad2446 100644 --- a/compiler/fir/raw-fir/psi2fir/tests/org/jetbrains/kotlin/fir/builder/AbstractRawFirBuilderTestCase.kt +++ b/compiler/fir/raw-fir/psi2fir/tests/org/jetbrains/kotlin/fir/builder/AbstractRawFirBuilderTestCase.kt
@@ -11,7 +11,8 @@ import com.intellij.psi.tree.IElementType import com.intellij.util.PathUtil import org.jetbrains.kotlin.KtNodeTypes -import org.jetbrains.kotlin.fir.* +import org.jetbrains.kotlin.fir.FirElement +import org.jetbrains.kotlin.fir.FirFunctionTypeParameter import org.jetbrains.kotlin.fir.contracts.impl.FirEmptyContractDescription import org.jetbrains.kotlin.fir.declarations.FirFile import org.jetbrains.kotlin.fir.declarations.FirTypeParameter @@ -24,6 +25,7 @@ import org.jetbrains.kotlin.fir.expressions.impl.FirNoReceiverExpression import org.jetbrains.kotlin.fir.expressions.impl.FirStubStatement import org.jetbrains.kotlin.fir.references.impl.FirStubReference +import org.jetbrains.kotlin.fir.render import org.jetbrains.kotlin.fir.renderer.FirRenderer import org.jetbrains.kotlin.fir.session.FirSessionFactoryHelper import org.jetbrains.kotlin.fir.types.FirTypeProjection @@ -179,7 +181,7 @@ private fun throwTwiceVisitingError(element: FirElement) { if (element is FirTypeRef || element is FirNoReceiverExpression || element is FirTypeParameter || - element is FirTypeProjection || element is FirValueParameter || element is FirAnnotation || + element is FirTypeProjection || element is FirValueParameter || element is FirAnnotation || element is FirFunctionTypeParameter || element is FirEmptyContractDescription || element is FirStubReference || element.isExtensionFunctionAnnotation || element is FirEmptyArgumentList || element is FirStubStatement || element === FirResolvedDeclarationStatusImpl.DEFAULT_STATUS_FOR_STATUSLESS_DECLARATIONS
diff --git a/compiler/fir/raw-fir/raw-fir.common/src/org/jetbrains/kotlin/fir/builder/BaseFirBuilder.kt b/compiler/fir/raw-fir/raw-fir.common/src/org/jetbrains/kotlin/fir/builder/BaseFirBuilder.kt index dd7e734..91374cf 100644 --- a/compiler/fir/raw-fir/raw-fir.common/src/org/jetbrains/kotlin/fir/builder/BaseFirBuilder.kt +++ b/compiler/fir/raw-fir/raw-fir.common/src/org/jetbrains/kotlin/fir/builder/BaseFirBuilder.kt
@@ -1290,7 +1290,6 @@ FUNCTION(shouldExplicitParameterTypeBePresent = true), CATCH(shouldExplicitParameterTypeBePresent = true), PRIMARY_CONSTRUCTOR(shouldExplicitParameterTypeBePresent = true), - FUNCTIONAL_TYPE(shouldExplicitParameterTypeBePresent = true), SETTER(shouldExplicitParameterTypeBePresent = false), LAMBDA(shouldExplicitParameterTypeBePresent = false), FOR_LOOP(shouldExplicitParameterTypeBePresent = false),
diff --git a/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/resolve/providers/impl/FirTypeResolverImpl.kt b/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/resolve/providers/impl/FirTypeResolverImpl.kt index 8a9c79e..ce94715 100644 --- a/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/resolve/providers/impl/FirTypeResolverImpl.kt +++ b/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/resolve/providers/impl/FirTypeResolverImpl.kt
@@ -466,7 +466,7 @@ val parameters = typeRef.contextReceiverTypeRefs.map { it.coneType } + listOfNotNull(typeRef.receiverTypeRef?.coneType) + - typeRef.valueParameters.map { it.returnTypeRef.coneType.withParameterNameAnnotation(it) } + + typeRef.parameters.map { it.returnTypeRef.coneType.withParameterNameAnnotation(it) } + listOf(typeRef.returnTypeRef.coneType) val classId = if (typeRef.isSuspend) { StandardClassIds.SuspendFunctionN(typeRef.parametersCount)
diff --git a/compiler/fir/tree/gen/org/jetbrains/kotlin/fir/FirFunctionTypeParameter.kt b/compiler/fir/tree/gen/org/jetbrains/kotlin/fir/FirFunctionTypeParameter.kt new file mode 100644 index 0000000..0c6a812 --- /dev/null +++ b/compiler/fir/tree/gen/org/jetbrains/kotlin/fir/FirFunctionTypeParameter.kt
@@ -0,0 +1,28 @@ +/* + * Copyright 2010-2022 JetBrains s.r.o. and Kotlin Programming Language contributors. + * Use of this source code is governed by the Apache 2.0 license that can be found in the license/LICENSE.txt file. + */ + +package org.jetbrains.kotlin.fir + +import org.jetbrains.kotlin.KtSourceElement +import org.jetbrains.kotlin.fir.types.FirTypeRef +import org.jetbrains.kotlin.name.Name +import org.jetbrains.kotlin.fir.visitors.* + +/* + * This file was generated automatically + * DO NOT MODIFY IT MANUALLY + */ + +abstract class FirFunctionTypeParameter : FirPureAbstractElement(), FirElement { + abstract override val source: KtSourceElement? + abstract val name: Name? + abstract val returnTypeRef: FirTypeRef + + override fun <R, D> accept(visitor: FirVisitor<R, D>, data: D): R = visitor.visitFunctionTypeParameter(this, data) + + @Suppress("UNCHECKED_CAST") + override fun <E: FirElement, D> transform(transformer: FirTransformer<D>, data: D): E = + transformer.transformFunctionTypeParameter(this, data) as E +}
diff --git a/compiler/fir/tree/gen/org/jetbrains/kotlin/fir/builder/FirFunctionTypeParameterBuilder.kt b/compiler/fir/tree/gen/org/jetbrains/kotlin/fir/builder/FirFunctionTypeParameterBuilder.kt new file mode 100644 index 0000000..b6ba158 --- /dev/null +++ b/compiler/fir/tree/gen/org/jetbrains/kotlin/fir/builder/FirFunctionTypeParameterBuilder.kt
@@ -0,0 +1,46 @@ +/* + * Copyright 2010-2022 JetBrains s.r.o. and Kotlin Programming Language contributors. + * Use of this source code is governed by the Apache 2.0 license that can be found in the license/LICENSE.txt file. + */ + +@file:Suppress("DuplicatedCode") + +package org.jetbrains.kotlin.fir.builder + +import kotlin.contracts.* +import org.jetbrains.kotlin.KtSourceElement +import org.jetbrains.kotlin.fir.FirFunctionTypeParameter +import org.jetbrains.kotlin.fir.builder.FirBuilderDsl +import org.jetbrains.kotlin.fir.impl.FirFunctionTypeParameterImpl +import org.jetbrains.kotlin.fir.types.FirTypeRef +import org.jetbrains.kotlin.fir.visitors.* +import org.jetbrains.kotlin.name.Name + +/* + * This file was generated automatically + * DO NOT MODIFY IT MANUALLY + */ + +@FirBuilderDsl +class FirFunctionTypeParameterBuilder { + var source: KtSourceElement? = null + var name: Name? = null + lateinit var returnTypeRef: FirTypeRef + + fun build(): FirFunctionTypeParameter { + return FirFunctionTypeParameterImpl( + source, + name, + returnTypeRef, + ) + } + +} + +@OptIn(ExperimentalContracts::class) +inline fun buildFunctionTypeParameter(init: FirFunctionTypeParameterBuilder.() -> Unit): FirFunctionTypeParameter { + contract { + callsInPlace(init, kotlin.contracts.InvocationKind.EXACTLY_ONCE) + } + return FirFunctionTypeParameterBuilder().apply(init).build() +}
diff --git a/compiler/fir/tree/gen/org/jetbrains/kotlin/fir/impl/FirFunctionTypeParameterImpl.kt b/compiler/fir/tree/gen/org/jetbrains/kotlin/fir/impl/FirFunctionTypeParameterImpl.kt new file mode 100644 index 0000000..fad3850 --- /dev/null +++ b/compiler/fir/tree/gen/org/jetbrains/kotlin/fir/impl/FirFunctionTypeParameterImpl.kt
@@ -0,0 +1,34 @@ +/* + * Copyright 2010-2022 JetBrains s.r.o. and Kotlin Programming Language contributors. + * Use of this source code is governed by the Apache 2.0 license that can be found in the license/LICENSE.txt file. + */ + +@file:Suppress("DuplicatedCode") + +package org.jetbrains.kotlin.fir.impl + +import org.jetbrains.kotlin.KtSourceElement +import org.jetbrains.kotlin.fir.FirFunctionTypeParameter +import org.jetbrains.kotlin.fir.types.FirTypeRef +import org.jetbrains.kotlin.name.Name +import org.jetbrains.kotlin.fir.visitors.* + +/* + * This file was generated automatically + * DO NOT MODIFY IT MANUALLY + */ + +internal class FirFunctionTypeParameterImpl( + override val source: KtSourceElement?, + override val name: Name?, + override var returnTypeRef: FirTypeRef, +) : FirFunctionTypeParameter() { + override fun <R, D> acceptChildren(visitor: FirVisitor<R, D>, data: D) { + returnTypeRef.accept(visitor, data) + } + + override fun <D> transformChildren(transformer: FirTransformer<D>, data: D): FirFunctionTypeParameterImpl { + returnTypeRef = returnTypeRef.transform(transformer, data) + return this + } +}
diff --git a/compiler/fir/tree/gen/org/jetbrains/kotlin/fir/types/FirFunctionTypeRef.kt b/compiler/fir/tree/gen/org/jetbrains/kotlin/fir/types/FirFunctionTypeRef.kt index 5d8164b..eb23437 100644 --- a/compiler/fir/tree/gen/org/jetbrains/kotlin/fir/types/FirFunctionTypeRef.kt +++ b/compiler/fir/tree/gen/org/jetbrains/kotlin/fir/types/FirFunctionTypeRef.kt
@@ -7,7 +7,7 @@ import org.jetbrains.kotlin.KtSourceElement import org.jetbrains.kotlin.fir.FirElement -import org.jetbrains.kotlin.fir.declarations.FirValueParameter +import org.jetbrains.kotlin.fir.FirFunctionTypeParameter import org.jetbrains.kotlin.fir.expressions.FirAnnotation import org.jetbrains.kotlin.fir.visitors.* @@ -21,7 +21,7 @@ abstract override val annotations: List<FirAnnotation> abstract override val isMarkedNullable: Boolean abstract val receiverTypeRef: FirTypeRef? - abstract val valueParameters: List<FirValueParameter> + abstract val parameters: List<FirFunctionTypeParameter> abstract val returnTypeRef: FirTypeRef abstract val isSuspend: Boolean abstract val contextReceiverTypeRefs: List<FirTypeRef>
diff --git a/compiler/fir/tree/gen/org/jetbrains/kotlin/fir/types/builder/FirFunctionTypeRefBuilder.kt b/compiler/fir/tree/gen/org/jetbrains/kotlin/fir/types/builder/FirFunctionTypeRefBuilder.kt index 67f9ba6..592ecdc 100644 --- a/compiler/fir/tree/gen/org/jetbrains/kotlin/fir/types/builder/FirFunctionTypeRefBuilder.kt +++ b/compiler/fir/tree/gen/org/jetbrains/kotlin/fir/types/builder/FirFunctionTypeRefBuilder.kt
@@ -9,9 +9,9 @@ import kotlin.contracts.* import org.jetbrains.kotlin.KtSourceElement +import org.jetbrains.kotlin.fir.FirFunctionTypeParameter import org.jetbrains.kotlin.fir.builder.FirAnnotationContainerBuilder import org.jetbrains.kotlin.fir.builder.FirBuilderDsl -import org.jetbrains.kotlin.fir.declarations.FirValueParameter import org.jetbrains.kotlin.fir.expressions.FirAnnotation import org.jetbrains.kotlin.fir.types.FirFunctionTypeRef import org.jetbrains.kotlin.fir.types.FirTypeRef @@ -29,7 +29,7 @@ override val annotations: MutableList<FirAnnotation> = mutableListOf() var isMarkedNullable: Boolean by kotlin.properties.Delegates.notNull<Boolean>() var receiverTypeRef: FirTypeRef? = null - val valueParameters: MutableList<FirValueParameter> = mutableListOf() + val parameters: MutableList<FirFunctionTypeParameter> = mutableListOf() lateinit var returnTypeRef: FirTypeRef var isSuspend: Boolean by kotlin.properties.Delegates.notNull<Boolean>() val contextReceiverTypeRefs: MutableList<FirTypeRef> = mutableListOf() @@ -40,7 +40,7 @@ annotations, isMarkedNullable, receiverTypeRef, - valueParameters, + parameters, returnTypeRef, isSuspend, contextReceiverTypeRefs, @@ -67,7 +67,7 @@ copyBuilder.annotations.addAll(original.annotations) copyBuilder.isMarkedNullable = original.isMarkedNullable copyBuilder.receiverTypeRef = original.receiverTypeRef - copyBuilder.valueParameters.addAll(original.valueParameters) + copyBuilder.parameters.addAll(original.parameters) copyBuilder.returnTypeRef = original.returnTypeRef copyBuilder.isSuspend = original.isSuspend copyBuilder.contextReceiverTypeRefs.addAll(original.contextReceiverTypeRefs)
diff --git a/compiler/fir/tree/gen/org/jetbrains/kotlin/fir/types/impl/FirFunctionTypeRefImpl.kt b/compiler/fir/tree/gen/org/jetbrains/kotlin/fir/types/impl/FirFunctionTypeRefImpl.kt index 1abf1fd..4ed0d5f 100644 --- a/compiler/fir/tree/gen/org/jetbrains/kotlin/fir/types/impl/FirFunctionTypeRefImpl.kt +++ b/compiler/fir/tree/gen/org/jetbrains/kotlin/fir/types/impl/FirFunctionTypeRefImpl.kt
@@ -8,7 +8,7 @@ package org.jetbrains.kotlin.fir.types.impl import org.jetbrains.kotlin.KtSourceElement -import org.jetbrains.kotlin.fir.declarations.FirValueParameter +import org.jetbrains.kotlin.fir.FirFunctionTypeParameter import org.jetbrains.kotlin.fir.expressions.FirAnnotation import org.jetbrains.kotlin.fir.types.FirFunctionTypeRef import org.jetbrains.kotlin.fir.types.FirTypeRef @@ -24,7 +24,7 @@ override val annotations: MutableList<FirAnnotation>, override val isMarkedNullable: Boolean, override var receiverTypeRef: FirTypeRef?, - override val valueParameters: MutableList<FirValueParameter>, + override val parameters: MutableList<FirFunctionTypeParameter>, override var returnTypeRef: FirTypeRef, override val isSuspend: Boolean, override val contextReceiverTypeRefs: MutableList<FirTypeRef>, @@ -32,7 +32,7 @@ override fun <R, D> acceptChildren(visitor: FirVisitor<R, D>, data: D) { annotations.forEach { it.accept(visitor, data) } receiverTypeRef?.accept(visitor, data) - valueParameters.forEach { it.accept(visitor, data) } + parameters.forEach { it.accept(visitor, data) } returnTypeRef.accept(visitor, data) contextReceiverTypeRefs.forEach { it.accept(visitor, data) } } @@ -40,7 +40,7 @@ override fun <D> transformChildren(transformer: FirTransformer<D>, data: D): FirFunctionTypeRefImpl { transformAnnotations(transformer, data) receiverTypeRef = receiverTypeRef?.transform(transformer, data) - valueParameters.transformInplace(transformer, data) + parameters.transformInplace(transformer, data) returnTypeRef = returnTypeRef.transform(transformer, data) contextReceiverTypeRefs.transformInplace(transformer, data) return this
diff --git a/compiler/fir/tree/gen/org/jetbrains/kotlin/fir/visitors/FirDefaultVisitor.kt b/compiler/fir/tree/gen/org/jetbrains/kotlin/fir/visitors/FirDefaultVisitor.kt index 9872139..5e665d8 100644 --- a/compiler/fir/tree/gen/org/jetbrains/kotlin/fir/visitors/FirDefaultVisitor.kt +++ b/compiler/fir/tree/gen/org/jetbrains/kotlin/fir/visitors/FirDefaultVisitor.kt
@@ -32,6 +32,7 @@ import org.jetbrains.kotlin.fir.declarations.FirProperty import org.jetbrains.kotlin.fir.declarations.FirField import org.jetbrains.kotlin.fir.declarations.FirEnumEntry +import org.jetbrains.kotlin.fir.FirFunctionTypeParameter import org.jetbrains.kotlin.fir.declarations.FirClassLikeDeclaration import org.jetbrains.kotlin.fir.declarations.FirClass import org.jetbrains.kotlin.fir.declarations.FirRegularClass
diff --git a/compiler/fir/tree/gen/org/jetbrains/kotlin/fir/visitors/FirDefaultVisitorVoid.kt b/compiler/fir/tree/gen/org/jetbrains/kotlin/fir/visitors/FirDefaultVisitorVoid.kt index cad24ee..5454bfb5 100644 --- a/compiler/fir/tree/gen/org/jetbrains/kotlin/fir/visitors/FirDefaultVisitorVoid.kt +++ b/compiler/fir/tree/gen/org/jetbrains/kotlin/fir/visitors/FirDefaultVisitorVoid.kt
@@ -32,6 +32,7 @@ import org.jetbrains.kotlin.fir.declarations.FirProperty import org.jetbrains.kotlin.fir.declarations.FirField import org.jetbrains.kotlin.fir.declarations.FirEnumEntry +import org.jetbrains.kotlin.fir.FirFunctionTypeParameter import org.jetbrains.kotlin.fir.declarations.FirClassLikeDeclaration import org.jetbrains.kotlin.fir.declarations.FirClass import org.jetbrains.kotlin.fir.declarations.FirRegularClass
diff --git a/compiler/fir/tree/gen/org/jetbrains/kotlin/fir/visitors/FirTransformer.kt b/compiler/fir/tree/gen/org/jetbrains/kotlin/fir/visitors/FirTransformer.kt index 717b941..d2c1295 100644 --- a/compiler/fir/tree/gen/org/jetbrains/kotlin/fir/visitors/FirTransformer.kt +++ b/compiler/fir/tree/gen/org/jetbrains/kotlin/fir/visitors/FirTransformer.kt
@@ -32,6 +32,7 @@ import org.jetbrains.kotlin.fir.declarations.FirProperty import org.jetbrains.kotlin.fir.declarations.FirField import org.jetbrains.kotlin.fir.declarations.FirEnumEntry +import org.jetbrains.kotlin.fir.FirFunctionTypeParameter import org.jetbrains.kotlin.fir.declarations.FirClassLikeDeclaration import org.jetbrains.kotlin.fir.declarations.FirClass import org.jetbrains.kotlin.fir.declarations.FirRegularClass @@ -255,6 +256,10 @@ return transformElement(enumEntry, data) } + open fun transformFunctionTypeParameter(functionTypeParameter: FirFunctionTypeParameter, data: D): FirFunctionTypeParameter { + return transformElement(functionTypeParameter, data) + } + open fun transformClassLikeDeclaration(classLikeDeclaration: FirClassLikeDeclaration, data: D): FirStatement { return transformElement(classLikeDeclaration, data) } @@ -799,6 +804,10 @@ return transformEnumEntry(enumEntry, data) } + final override fun visitFunctionTypeParameter(functionTypeParameter: FirFunctionTypeParameter, data: D): FirFunctionTypeParameter { + return transformFunctionTypeParameter(functionTypeParameter, data) + } + final override fun visitClassLikeDeclaration(classLikeDeclaration: FirClassLikeDeclaration, data: D): FirStatement { return transformClassLikeDeclaration(classLikeDeclaration, data) }
diff --git a/compiler/fir/tree/gen/org/jetbrains/kotlin/fir/visitors/FirVisitor.kt b/compiler/fir/tree/gen/org/jetbrains/kotlin/fir/visitors/FirVisitor.kt index d095436..33d5d8f 100644 --- a/compiler/fir/tree/gen/org/jetbrains/kotlin/fir/visitors/FirVisitor.kt +++ b/compiler/fir/tree/gen/org/jetbrains/kotlin/fir/visitors/FirVisitor.kt
@@ -32,6 +32,7 @@ import org.jetbrains.kotlin.fir.declarations.FirProperty import org.jetbrains.kotlin.fir.declarations.FirField import org.jetbrains.kotlin.fir.declarations.FirEnumEntry +import org.jetbrains.kotlin.fir.FirFunctionTypeParameter import org.jetbrains.kotlin.fir.declarations.FirClassLikeDeclaration import org.jetbrains.kotlin.fir.declarations.FirClass import org.jetbrains.kotlin.fir.declarations.FirRegularClass @@ -202,6 +203,8 @@ open fun visitEnumEntry(enumEntry: FirEnumEntry, data: D): R = visitElement(enumEntry, data) + open fun visitFunctionTypeParameter(functionTypeParameter: FirFunctionTypeParameter, data: D): R = visitElement(functionTypeParameter, data) + open fun visitClassLikeDeclaration(classLikeDeclaration: FirClassLikeDeclaration, data: D): R = visitElement(classLikeDeclaration, data) open fun visitClass(klass: FirClass, data: D): R = visitElement(klass, data)
diff --git a/compiler/fir/tree/gen/org/jetbrains/kotlin/fir/visitors/FirVisitorVoid.kt b/compiler/fir/tree/gen/org/jetbrains/kotlin/fir/visitors/FirVisitorVoid.kt index 20b1745..26ebeac 100644 --- a/compiler/fir/tree/gen/org/jetbrains/kotlin/fir/visitors/FirVisitorVoid.kt +++ b/compiler/fir/tree/gen/org/jetbrains/kotlin/fir/visitors/FirVisitorVoid.kt
@@ -32,6 +32,7 @@ import org.jetbrains.kotlin.fir.declarations.FirProperty import org.jetbrains.kotlin.fir.declarations.FirField import org.jetbrains.kotlin.fir.declarations.FirEnumEntry +import org.jetbrains.kotlin.fir.FirFunctionTypeParameter import org.jetbrains.kotlin.fir.declarations.FirClassLikeDeclaration import org.jetbrains.kotlin.fir.declarations.FirClass import org.jetbrains.kotlin.fir.declarations.FirRegularClass @@ -254,6 +255,10 @@ visitElement(enumEntry) } + open fun visitFunctionTypeParameter(functionTypeParameter: FirFunctionTypeParameter) { + visitElement(functionTypeParameter) + } + open fun visitClassLikeDeclaration(classLikeDeclaration: FirClassLikeDeclaration) { visitElement(classLikeDeclaration) } @@ -798,6 +803,10 @@ visitEnumEntry(enumEntry) } + final override fun visitFunctionTypeParameter(functionTypeParameter: FirFunctionTypeParameter, data: Nothing?) { + visitFunctionTypeParameter(functionTypeParameter) + } + final override fun visitClassLikeDeclaration(classLikeDeclaration: FirClassLikeDeclaration, data: Nothing?) { visitClassLikeDeclaration(classLikeDeclaration) }
diff --git a/compiler/fir/tree/src/org/jetbrains/kotlin/fir/renderer/FirRenderer.kt b/compiler/fir/tree/src/org/jetbrains/kotlin/fir/renderer/FirRenderer.kt index 702038d..cc1954e 100644 --- a/compiler/fir/tree/src/org/jetbrains/kotlin/fir/renderer/FirRenderer.kt +++ b/compiler/fir/tree/src/org/jetbrains/kotlin/fir/renderer/FirRenderer.kt
@@ -707,7 +707,20 @@ it.accept(this) print(".") } - valueParameterRenderer.renderParameters(functionTypeRef.valueParameters) + + printer.print("(") + for ((index, parameter) in functionTypeRef.parameters.withIndex()) { + if (index > 0) { + printer.print(", ") + } + parameter.name?.let { name -> + printer.print(name.asString()) + printer.print(": ") + } + parameter.returnTypeRef.accept(visitor) + } + printer.print(")") + print(" -> ") functionTypeRef.returnTypeRef.accept(this) print(" )")
diff --git a/compiler/fir/tree/src/org/jetbrains/kotlin/fir/types/FirTypeUtils.kt b/compiler/fir/tree/src/org/jetbrains/kotlin/fir/types/FirTypeUtils.kt index fdb235d..2efce30 100644 --- a/compiler/fir/tree/src/org/jetbrains/kotlin/fir/types/FirTypeUtils.kt +++ b/compiler/fir/tree/src/org/jetbrains/kotlin/fir/types/FirTypeUtils.kt
@@ -77,9 +77,9 @@ val FirFunctionTypeRef.parametersCount: Int get() = if (receiverTypeRef != null) - valueParameters.size + contextReceiverTypeRefs.size + 1 + parameters.size + contextReceiverTypeRefs.size + 1 else - valueParameters.size + contextReceiverTypeRefs.size + parameters.size + contextReceiverTypeRefs.size val EXTENSION_FUNCTION_ANNOTATION = ClassId.fromString("kotlin/ExtensionFunctionType") val INTRINSIC_CONST_EVALUATION_ANNOTATION = ClassId.fromString("kotlin/internal/IntrinsicConstEvaluation")
diff --git a/compiler/fir/tree/tree-generator/src/org/jetbrains/kotlin/fir/tree/generator/FirTreeBuilder.kt b/compiler/fir/tree/tree-generator/src/org/jetbrains/kotlin/fir/tree/generator/FirTreeBuilder.kt index 79d3194..5342084 100644 --- a/compiler/fir/tree/tree-generator/src/org/jetbrains/kotlin/fir/tree/generator/FirTreeBuilder.kt +++ b/compiler/fir/tree/tree-generator/src/org/jetbrains/kotlin/fir/tree/generator/FirTreeBuilder.kt
@@ -45,6 +45,8 @@ val field by element(Declaration, variable, controlFlowGraphOwner) val enumEntry by element(Declaration, variable) + val functionTypeParameter by element(Other, baseFirElement) + val classLikeDeclaration by sealedElement(Declaration, memberDeclaration, statement) val klass by sealedElement("Class", Declaration, classLikeDeclaration, statement, typeParameterRefsOwner) val regularClass by element(Declaration, klass, controlFlowGraphOwner)
diff --git a/compiler/fir/tree/tree-generator/src/org/jetbrains/kotlin/fir/tree/generator/NodeConfigurator.kt b/compiler/fir/tree/tree-generator/src/org/jetbrains/kotlin/fir/tree/generator/NodeConfigurator.kt index 1e72181..6e4bcb2 100644 --- a/compiler/fir/tree/tree-generator/src/org/jetbrains/kotlin/fir/tree/generator/NodeConfigurator.kt +++ b/compiler/fir/tree/tree-generator/src/org/jetbrains/kotlin/fir/tree/generator/NodeConfigurator.kt
@@ -411,6 +411,12 @@ needTransformOtherChildren() } + + functionTypeParameter.configure { + +field("name", nameType, nullable = true) + +field("returnTypeRef", typeRef) + } + errorProperty.configure { +symbol("FirErrorPropertySymbol") } @@ -640,7 +646,7 @@ functionTypeRef.configure { +field("receiverTypeRef", typeRef, nullable = true) - +valueParameters + +fieldList("parameters", functionTypeParameter) +returnTypeRef +booleanField("isSuspend")
diff --git a/compiler/testData/diagnostics/tests/Bounds.fir.kt b/compiler/testData/diagnostics/tests/Bounds.fir.kt index 50567a8..2efca46 100644 --- a/compiler/testData/diagnostics/tests/Bounds.fir.kt +++ b/compiler/testData/diagnostics/tests/Bounds.fir.kt
@@ -20,10 +20,10 @@ class Pair<A, B> - abstract class C<T : B<<!UPPER_BOUND_VIOLATED!>Int<!>>, X : (B<<!UPPER_BOUND_VIOLATED, UPPER_BOUND_VIOLATED!>Char<!>>) -> Pair<B<<!UPPER_BOUND_VIOLATED!>Any<!>>, B<A>>>() : B<<!UPPER_BOUND_VIOLATED!>Any<!>>() { // 2 errors + abstract class C<T : B<<!UPPER_BOUND_VIOLATED!>Int<!>>, X : (B<<!UPPER_BOUND_VIOLATED!>Char<!>>) -> Pair<B<<!UPPER_BOUND_VIOLATED!>Any<!>>, B<A>>>() : B<<!UPPER_BOUND_VIOLATED!>Any<!>>() { // 2 errors val a = B<<!UPPER_BOUND_VIOLATED!>Char<!>>() // error - abstract val x : (B<<!UPPER_BOUND_VIOLATED, UPPER_BOUND_VIOLATED!>Char<!>>) -> B<<!UPPER_BOUND_VIOLATED!>Any<!>> + abstract val x : (B<<!UPPER_BOUND_VIOLATED!>Char<!>>) -> B<<!UPPER_BOUND_VIOLATED!>Any<!>> }
diff --git a/compiler/testData/diagnostics/tests/DefaultValueForParameterInFunctionType.kt b/compiler/testData/diagnostics/tests/DefaultValueForParameterInFunctionType.kt index e32d9b8..77169ad 100644 --- a/compiler/testData/diagnostics/tests/DefaultValueForParameterInFunctionType.kt +++ b/compiler/testData/diagnostics/tests/DefaultValueForParameterInFunctionType.kt
@@ -17,5 +17,5 @@ } val prop: (x: Int = <!UNSUPPORTED!>0<!>)->Unit - get(): (x: Int = <!UNSUPPORTED!>0<!>)->Unit = {} + get(): (x: Int = <!UNSUPPORTED!>0<!>)->Unit = {} }
diff --git a/compiler/testData/diagnostics/tests/incompleteCode/diagnosticWithSyntaxError/typeReferenceError.fir.kt b/compiler/testData/diagnostics/tests/incompleteCode/diagnosticWithSyntaxError/typeReferenceError.fir.kt index aa5f5d1..aaf1271 100644 --- a/compiler/testData/diagnostics/tests/incompleteCode/diagnosticWithSyntaxError/typeReferenceError.fir.kt +++ b/compiler/testData/diagnostics/tests/incompleteCode/diagnosticWithSyntaxError/typeReferenceError.fir.kt
@@ -1,3 +1,3 @@ package typeReferenceError -<!ABSTRACT_MEMBER_NOT_IMPLEMENTED!>class Pair<!><<!SYNTAX!><!>:<!UNRESOLVED_REFERENCE!>(val c: <!SYNTAX!><!SYNTAX!><!>fun<!><!SYNTAX!><!> <!UNRESOLVED_REFERENCE!>main<!><!>() +<!ABSTRACT_MEMBER_NOT_IMPLEMENTED!>class Pair<!><<!SYNTAX!><!>:<!UNRESOLVED_REFERENCE!>(<!UNSUPPORTED!>val<!> c: <!SYNTAX!><!SYNTAX!><!>fun<!><!SYNTAX!><!> <!UNRESOLVED_REFERENCE!>main<!><!>()
diff --git a/compiler/testData/diagnostics/tests/modifiers/modifierOnParameterInFunctionType.fir.kt b/compiler/testData/diagnostics/tests/modifiers/modifierOnParameterInFunctionType.fir.kt deleted file mode 100644 index 4cdb4dd..0000000 --- a/compiler/testData/diagnostics/tests/modifiers/modifierOnParameterInFunctionType.fir.kt +++ /dev/null
@@ -1,52 +0,0 @@ -// !DIAGNOSTICS: -UNUSED_PARAMETER -UNUSED_VARIABLE - -fun f(vararg x: Int) {} - -val inVal: (<!WRONG_MODIFIER_CONTAINING_DECLARATION!>vararg<!> x: Int)->Unit = {} - -fun inParam(fn: (<!WRONG_MODIFIER_CONTAINING_DECLARATION!>vararg<!> x: Int)->Unit) {} - -fun inParamNested(fn1: (fn2: (<!WRONG_MODIFIER_CONTAINING_DECLARATION!>vararg<!> n: Int)->Unit)->Unit) {} - -fun inReturn(): (vararg x: Int)->Unit = {} - -class A : (vararg Int)->Unit { - override fun invoke(p1: Int) { - var lambda: (vararg x: Int)->Unit = {} - } - - val prop: (vararg x: Int)->Unit - get(): (<!WRONG_MODIFIER_CONTAINING_DECLARATION!>vararg<!> x: Int)->Unit = {} -} - -val allProhibited: (<!REDUNDANT_MODIFIER, WRONG_MODIFIER_TARGET!>abstract<!> - <!WRONG_MODIFIER_TARGET!>annotation<!> - <!WRONG_MODIFIER_TARGET!>companion<!> - <!INCOMPATIBLE_MODIFIERS!>const<!> - <!INCOMPATIBLE_MODIFIERS!>crossinline<!> - <!INCOMPATIBLE_MODIFIERS!>data<!> - <!WRONG_MODIFIER_TARGET!>enum<!> - <!WRONG_MODIFIER_TARGET!>external<!> - <!INCOMPATIBLE_MODIFIERS!>final<!> - <!WRONG_MODIFIER_TARGET!>in<!> - <!INCOMPATIBLE_MODIFIERS!>inline<!> - <!INCOMPATIBLE_MODIFIERS!>inner<!> - <!WRONG_MODIFIER_TARGET!>internal<!> - <!WRONG_MODIFIER_TARGET!>lateinit<!> - <!INCOMPATIBLE_MODIFIERS!>noinline<!> - <!INCOMPATIBLE_MODIFIERS, REDUNDANT_MODIFIER!>open<!> - <!WRONG_MODIFIER_TARGET!>operator<!> - <!INCOMPATIBLE_MODIFIERS!>out<!> - <!INCOMPATIBLE_MODIFIERS!>override<!> - <!INCOMPATIBLE_MODIFIERS!>private<!> - <!INCOMPATIBLE_MODIFIERS!>protected<!> - <!INCOMPATIBLE_MODIFIERS!>public<!> - <!WRONG_MODIFIER_TARGET!>reified<!> - <!INCOMPATIBLE_MODIFIERS!>sealed<!> - <!WRONG_MODIFIER_TARGET!>tailrec<!> - <!WRONG_MODIFIER_CONTAINING_DECLARATION!>vararg<!> - - x: Int)->Unit = {} - -val valProhibited: (val x: Int)->Unit = {} -val varProhibited: (var x: Int)->Unit = {}
diff --git a/compiler/testData/diagnostics/tests/modifiers/modifierOnParameterInFunctionType.kt b/compiler/testData/diagnostics/tests/modifiers/modifierOnParameterInFunctionType.kt index d70d565..07d8b38 100644 --- a/compiler/testData/diagnostics/tests/modifiers/modifierOnParameterInFunctionType.kt +++ b/compiler/testData/diagnostics/tests/modifiers/modifierOnParameterInFunctionType.kt
@@ -1,3 +1,4 @@ +// FIR_IDENTICAL // !DIAGNOSTICS: -UNUSED_PARAMETER -UNUSED_VARIABLE fun f(vararg x: Int) {} @@ -49,4 +50,4 @@ x: Int)->Unit = {} val valProhibited: (<!UNSUPPORTED!>val<!> x: Int)->Unit = {} -val varProhibited: (<!UNSUPPORTED!>var<!> x: Int)->Unit = {} \ No newline at end of file +val varProhibited: (<!UNSUPPORTED!>var<!> x: Int)->Unit = {}