From ec7caba8ea4998307f823a71fdfa09a9ddd8009e Mon Sep 17 00:00:00 2001 From: Mikhail Glukhikh Date: Wed, 15 Nov 2023 14:39:39 +0100 Subject: [PATCH] K2: restore smart cast in case with invisible receiver but visible callable Related to KT-52432 #KT-63164 Fixed --- .../fir/resolve/calls/VisibilityUtils.kt | 7 ++- ...smartCastToInvisibleClassMember.fir.ir.txt | 61 ------------------- .../fir/smartCastToInvisibleClassMember.kt | 3 +- 3 files changed, 7 insertions(+), 64 deletions(-) delete mode 100644 compiler/testData/codegen/box/fir/smartCastToInvisibleClassMember.fir.ir.txt diff --git a/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/resolve/calls/VisibilityUtils.kt b/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/resolve/calls/VisibilityUtils.kt index 1c5fed31941..4b7f09cbb4d 100644 --- a/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/resolve/calls/VisibilityUtils.kt +++ b/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/resolve/calls/VisibilityUtils.kt @@ -71,7 +71,12 @@ fun FirVisibilityChecker.isVisible( if (!isVisible(declaration, callInfo, dispatchReceiverWithoutSmartCastType, skipCheckForContainingClassVisibility)) return false - candidate.dispatchReceiver = dispatchReceiverWithoutSmartCastType + // Note: in case of a smart cast, we already checked the visibility of the smart cast target before, + // so now it's visibility is not important, only callable visibility itself should be taken into account + // Otherwise we avoid correct smart casts in corner cases like KT-63164 + if (!isVisible(declaration, callInfo, candidate.dispatchReceiver, skipCheckForContainingClassVisibility = true)) { + candidate.dispatchReceiver = dispatchReceiverWithoutSmartCastType + } } val backingField = declaration.getBackingFieldIfApplicable() diff --git a/compiler/testData/codegen/box/fir/smartCastToInvisibleClassMember.fir.ir.txt b/compiler/testData/codegen/box/fir/smartCastToInvisibleClassMember.fir.ir.txt deleted file mode 100644 index a4167babb0a..00000000000 --- a/compiler/testData/codegen/box/fir/smartCastToInvisibleClassMember.fir.ir.txt +++ /dev/null @@ -1,61 +0,0 @@ -Module: m1 -FILE fqName: fileName:/info.kt - CLASS CLASS name:Info modality:FINAL visibility:internal superTypes:[kotlin.Any] - $this: VALUE_PARAMETER INSTANCE_RECEIVER name: type:.Info - CONSTRUCTOR visibility:public <> () returnType:.Info [primary] - BLOCK_BODY - DELEGATING_CONSTRUCTOR_CALL 'public constructor () declared in kotlin.Any' - INSTANCE_INITIALIZER_CALL classDescriptor='CLASS CLASS name:Info modality:FINAL visibility:internal superTypes:[kotlin.Any]' - PROPERTY name:status visibility:public modality:FINAL [val] - FIELD PROPERTY_BACKING_FIELD name:status type:kotlin.String visibility:private [final] - EXPRESSION_BODY - CONST String type=kotlin.String value="OK" - FUN DEFAULT_PROPERTY_ACCESSOR name: visibility:public modality:FINAL <> ($this:.Info) returnType:kotlin.String - correspondingProperty: PROPERTY name:status visibility:public modality:FINAL [val] - $this: VALUE_PARAMETER name: type:.Info - BLOCK_BODY - RETURN type=kotlin.Nothing from='public final fun (): kotlin.String declared in .Info' - GET_FIELD 'FIELD PROPERTY_BACKING_FIELD name:status type:kotlin.String visibility:private [final]' type=kotlin.String origin=null - receiver: GET_VAR ': .Info declared in .Info.' type=.Info origin=null - FUN FAKE_OVERRIDE name:equals visibility:public modality:OPEN <> ($this:kotlin.Any, other:kotlin.Any?) returnType:kotlin.Boolean [fake_override,operator] - overridden: - public open fun equals (other: kotlin.Any?): kotlin.Boolean declared in kotlin.Any - $this: VALUE_PARAMETER name: type:kotlin.Any - VALUE_PARAMETER name:other index:0 type:kotlin.Any? - FUN FAKE_OVERRIDE name:hashCode visibility:public modality:OPEN <> ($this:kotlin.Any) returnType:kotlin.Int [fake_override] - overridden: - public open fun hashCode (): kotlin.Int declared in kotlin.Any - $this: VALUE_PARAMETER name: type:kotlin.Any - FUN FAKE_OVERRIDE name:toString visibility:public modality:OPEN <> ($this:kotlin.Any) returnType:kotlin.String [fake_override] - overridden: - public open fun toString (): kotlin.String declared in kotlin.Any - $this: VALUE_PARAMETER name: type:kotlin.Any - PROPERTY name:info visibility:public modality:FINAL [val] - FIELD PROPERTY_BACKING_FIELD name:info type:kotlin.Any? visibility:private [final,static] - EXPRESSION_BODY - CONSTRUCTOR_CALL 'public constructor () declared in .Info' type=.Info origin=null - FUN DEFAULT_PROPERTY_ACCESSOR name: visibility:public modality:FINAL <> () returnType:kotlin.Any? - correspondingProperty: PROPERTY name:info visibility:public modality:FINAL [val] - BLOCK_BODY - RETURN type=kotlin.Nothing from='public final fun (): kotlin.Any? declared in ' - GET_FIELD 'FIELD PROPERTY_BACKING_FIELD name:info type:kotlin.Any? visibility:private [final,static]' type=kotlin.Any? origin=null -Module: m2 -FILE fqName: fileName:/box.kt - FUN name:getStatus visibility:public modality:FINAL <> (param:kotlin.Any?) returnType:kotlin.String - VALUE_PARAMETER name:param index:0 type:kotlin.Any? - BLOCK_BODY - WHEN type=kotlin.Unit origin=IF - BRANCH - if: TYPE_OP type=kotlin.Boolean origin=INSTANCEOF typeOperand=.Info - GET_VAR 'param: kotlin.Any? declared in .getStatus' type=kotlin.Any? origin=null - then: BLOCK type=kotlin.Unit origin=null - RETURN type=kotlin.Nothing from='public final fun getStatus (param: kotlin.Any?): kotlin.String declared in ' - CALL 'public final fun (): kotlin.String declared in kotlin.Any' type=kotlin.String origin=GET_PROPERTY - $this: GET_VAR 'param: kotlin.Any? declared in .getStatus' type=kotlin.Any? origin=null - RETURN type=kotlin.Nothing from='public final fun getStatus (param: kotlin.Any?): kotlin.String declared in ' - CONST String type=kotlin.String value="NO STATUS" - FUN name:box visibility:public modality:FINAL <> () returnType:kotlin.String - BLOCK_BODY - RETURN type=kotlin.Nothing from='public final fun box (): kotlin.String declared in ' - CALL 'public final fun getStatus (param: kotlin.Any?): kotlin.String declared in ' type=kotlin.String origin=null - param: CALL 'public final fun (): kotlin.Any? declared in ' type=kotlin.Any? origin=GET_PROPERTY diff --git a/compiler/testData/codegen/box/fir/smartCastToInvisibleClassMember.kt b/compiler/testData/codegen/box/fir/smartCastToInvisibleClassMember.kt index 7bb0a061e22..a8f11cb5b15 100644 --- a/compiler/testData/codegen/box/fir/smartCastToInvisibleClassMember.kt +++ b/compiler/testData/codegen/box/fir/smartCastToInvisibleClassMember.kt @@ -1,7 +1,6 @@ -// IGNORE_BACKEND_K2: JVM_IR, JS_IR, NATIVE, WASM -// FIR status: see KT-63164 // ISSUE: KT-63164 // DUMP_IR +// FIR_IDENTICAL // MODULE: m1 // FILE: info.kt