[FIR] Fix propagating expected type for binary operator calls
This commit is contained in:
+9
@@ -740,6 +740,15 @@ open class FirBodyResolveTransformer(
|
||||
}
|
||||
}
|
||||
|
||||
override fun transformOperatorCall(operatorCall: FirOperatorCall, data: Any?): CompositeTransformResult<FirStatement> {
|
||||
if (operatorCall.operation in FirOperation.BOOLEANS) {
|
||||
return (operatorCall.transformChildren(this, noExpectedType) as FirOperatorCall).also {
|
||||
it.resultType = booleanType
|
||||
}.compose()
|
||||
}
|
||||
return super.transformOperatorCall(operatorCall, data)
|
||||
}
|
||||
|
||||
// ----------------------- Util functions -----------------------
|
||||
|
||||
private inline fun <T> withLabelAndReceiverType(labelName: Name, owner: FirElement, type: ConeKotlinType, block: () -> T): T {
|
||||
|
||||
@@ -8,4 +8,4 @@ FILE fqName:<root> fileName:/localVarInDoWhile.kt
|
||||
condition: CALL 'public final fun not (): kotlin.Boolean declared in kotlin.Boolean' type=kotlin.Boolean origin=EXCLEQ
|
||||
$this: CALL 'public final fun EQEQ (arg0: kotlin.Any?, arg1: kotlin.Any?): kotlin.Boolean declared in kotlin.internal.ir' type=kotlin.Boolean origin=EXCLEQ
|
||||
arg0: GET_VAR 'val x: kotlin.Int [val] declared in <root>.foo' type=kotlin.Int origin=null
|
||||
arg1: CONST Int type=kotlin.Unit value=42
|
||||
arg1: CONST Int type=kotlin.Int value=42
|
||||
|
||||
Vendored
+8
-8
@@ -19,7 +19,7 @@ FILE fqName:<root> fileName:/floatingPointCompareTo.kt
|
||||
then: CALL 'public final fun EQEQ (arg0: kotlin.Any?, arg1: kotlin.Any?): kotlin.Boolean declared in kotlin.internal.ir' type=kotlin.Boolean origin=EQEQ
|
||||
arg0: ERROR_CALL 'Unresolved reference: <Inapplicable(INAPPLICABLE): [kotlin/Double.compareTo, kotlin/Double.compareTo, kotlin/Double.compareTo, kotlin/Double.compareTo, kotlin/Double.compareTo, kotlin/Double.compareTo]>#' type=IrErrorType
|
||||
GET_VAR 'y: kotlin.Any declared in <root>.test2d' type=kotlin.Any origin=null
|
||||
arg1: CONST Int type=kotlin.Boolean value=0
|
||||
arg1: CONST Int type=kotlin.Int value=0
|
||||
BRANCH
|
||||
if: CONST Boolean type=kotlin.Boolean value=true
|
||||
then: CONST Boolean type=kotlin.Boolean value=false
|
||||
@@ -42,7 +42,7 @@ FILE fqName:<root> fileName:/floatingPointCompareTo.kt
|
||||
then: CALL 'public final fun EQEQ (arg0: kotlin.Any?, arg1: kotlin.Any?): kotlin.Boolean declared in kotlin.internal.ir' type=kotlin.Boolean origin=EQEQ
|
||||
arg0: ERROR_CALL 'Unresolved reference: <Unresolved name: compareTo>#' type=IrErrorType
|
||||
GET_VAR 'y: kotlin.Any declared in <root>.test3d' type=kotlin.Any origin=null
|
||||
arg1: CONST Int type=kotlin.Boolean value=0
|
||||
arg1: CONST Int type=kotlin.Int value=0
|
||||
BRANCH
|
||||
if: CONST Boolean type=kotlin.Boolean value=true
|
||||
then: CONST Boolean type=kotlin.Boolean value=false
|
||||
@@ -66,7 +66,7 @@ FILE fqName:<root> fileName:/floatingPointCompareTo.kt
|
||||
then: CALL 'public final fun EQEQ (arg0: kotlin.Any?, arg1: kotlin.Any?): kotlin.Boolean declared in kotlin.internal.ir' type=kotlin.Boolean origin=EQEQ
|
||||
arg0: ERROR_CALL 'Unresolved reference: <Inapplicable(INAPPLICABLE): [kotlin/Float.compareTo, kotlin/Float.compareTo, kotlin/Float.compareTo, kotlin/Float.compareTo, kotlin/Float.compareTo, kotlin/Float.compareTo]>#' type=IrErrorType
|
||||
GET_VAR 'y: kotlin.Any declared in <root>.test2f' type=kotlin.Any origin=null
|
||||
arg1: CONST Int type=kotlin.Boolean value=0
|
||||
arg1: CONST Int type=kotlin.Int value=0
|
||||
BRANCH
|
||||
if: CONST Boolean type=kotlin.Boolean value=true
|
||||
then: CONST Boolean type=kotlin.Boolean value=false
|
||||
@@ -89,7 +89,7 @@ FILE fqName:<root> fileName:/floatingPointCompareTo.kt
|
||||
then: CALL 'public final fun EQEQ (arg0: kotlin.Any?, arg1: kotlin.Any?): kotlin.Boolean declared in kotlin.internal.ir' type=kotlin.Boolean origin=EQEQ
|
||||
arg0: ERROR_CALL 'Unresolved reference: <Unresolved name: compareTo>#' type=IrErrorType
|
||||
GET_VAR 'y: kotlin.Any declared in <root>.test3f' type=kotlin.Any origin=null
|
||||
arg1: CONST Int type=kotlin.Boolean value=0
|
||||
arg1: CONST Int type=kotlin.Int value=0
|
||||
BRANCH
|
||||
if: CONST Boolean type=kotlin.Boolean value=true
|
||||
then: CONST Boolean type=kotlin.Boolean value=false
|
||||
@@ -112,7 +112,7 @@ FILE fqName:<root> fileName:/floatingPointCompareTo.kt
|
||||
then: CALL 'public final fun EQEQ (arg0: kotlin.Any?, arg1: kotlin.Any?): kotlin.Boolean declared in kotlin.internal.ir' type=kotlin.Boolean origin=EQEQ
|
||||
arg0: ERROR_CALL 'Unresolved reference: <Unresolved name: compareTo>#' type=IrErrorType
|
||||
GET_VAR 'y: kotlin.Any declared in <root>.testFD' type=kotlin.Any origin=null
|
||||
arg1: CONST Int type=kotlin.Boolean value=0
|
||||
arg1: CONST Int type=kotlin.Int value=0
|
||||
BRANCH
|
||||
if: CONST Boolean type=kotlin.Boolean value=true
|
||||
then: CONST Boolean type=kotlin.Boolean value=false
|
||||
@@ -135,7 +135,7 @@ FILE fqName:<root> fileName:/floatingPointCompareTo.kt
|
||||
then: CALL 'public final fun EQEQ (arg0: kotlin.Any?, arg1: kotlin.Any?): kotlin.Boolean declared in kotlin.internal.ir' type=kotlin.Boolean origin=EQEQ
|
||||
arg0: ERROR_CALL 'Unresolved reference: <Unresolved name: compareTo>#' type=IrErrorType
|
||||
GET_VAR 'y: kotlin.Any declared in <root>.testDF' type=kotlin.Any origin=null
|
||||
arg1: CONST Int type=kotlin.Boolean value=0
|
||||
arg1: CONST Int type=kotlin.Int value=0
|
||||
BRANCH
|
||||
if: CONST Boolean type=kotlin.Boolean value=true
|
||||
then: CONST Boolean type=kotlin.Boolean value=false
|
||||
@@ -158,7 +158,7 @@ FILE fqName:<root> fileName:/floatingPointCompareTo.kt
|
||||
then: CALL 'public final fun EQEQ (arg0: kotlin.Any?, arg1: kotlin.Any?): kotlin.Boolean declared in kotlin.internal.ir' type=kotlin.Boolean origin=EQEQ
|
||||
arg0: ERROR_CALL 'Unresolved reference: <Inapplicable(INAPPLICABLE): [kotlin/Float.compareTo, kotlin/Float.compareTo, kotlin/Float.compareTo, kotlin/Float.compareTo, kotlin/Float.compareTo, kotlin/Float.compareTo]>#' type=IrErrorType
|
||||
GET_VAR 'x: kotlin.Any declared in <root>.test2fr' type=kotlin.Any origin=null
|
||||
arg1: CONST Int type=kotlin.Boolean value=0
|
||||
arg1: CONST Int type=kotlin.Int value=0
|
||||
BRANCH
|
||||
if: CONST Boolean type=kotlin.Boolean value=true
|
||||
then: CONST Boolean type=kotlin.Boolean value=false
|
||||
@@ -174,7 +174,7 @@ FILE fqName:<root> fileName:/floatingPointCompareTo.kt
|
||||
then: CALL 'public final fun EQEQ (arg0: kotlin.Any?, arg1: kotlin.Any?): kotlin.Boolean declared in kotlin.internal.ir' type=kotlin.Boolean origin=EQEQ
|
||||
arg0: ERROR_CALL 'Unresolved reference: <Inapplicable(INAPPLICABLE): [kotlin/Float.compareTo, kotlin/Float.compareTo, kotlin/Float.compareTo, kotlin/Float.compareTo, kotlin/Float.compareTo, kotlin/Float.compareTo]>#' type=IrErrorType
|
||||
GET_VAR 'x: kotlin.Any declared in <root>.test3fr' type=kotlin.Any origin=null
|
||||
arg1: CONST Int type=kotlin.Boolean value=0
|
||||
arg1: CONST Int type=kotlin.Int value=0
|
||||
BRANCH
|
||||
if: CONST Boolean type=kotlin.Boolean value=true
|
||||
then: CONST Boolean type=kotlin.Boolean value=false
|
||||
|
||||
@@ -71,7 +71,9 @@ FILE fqName:<root> fileName:/forWithImplicitReceivers.kt
|
||||
$receiver: VALUE_PARAMETER name:<this> type:<root>.IntCell
|
||||
BLOCK_BODY
|
||||
RETURN type=kotlin.Nothing from='public open fun hasNext (): kotlin.Boolean declared in <root>.IReceiver'
|
||||
ERROR_CALL 'Comparison of arguments with different types: kotlin/Int, kotlin/Boolean' type=kotlin.Boolean
|
||||
CALL 'public final fun greater (arg0: kotlin.Int, arg1: kotlin.Int): kotlin.Boolean declared in kotlin.internal.ir' type=kotlin.Boolean origin=GT
|
||||
arg0: CALL 'public final fun <get-value> (): kotlin.Int declared in <root>.IntCell' type=kotlin.Int origin=null
|
||||
arg1: CONST Int type=kotlin.Int value=0
|
||||
FUN name:next visibility:public modality:OPEN <> ($this:<root>.IReceiver, $receiver:<root>.IntCell) returnType:kotlin.Int
|
||||
$this: VALUE_PARAMETER name:<this> type:<root>.IReceiver
|
||||
$receiver: VALUE_PARAMETER name:<this> type:<root>.IntCell
|
||||
|
||||
+9
-9
@@ -98,25 +98,25 @@ FILE fqName:<root> fileName:/when.kt
|
||||
BRANCH
|
||||
if: CALL 'public final fun EQEQ (arg0: kotlin.Any?, arg1: kotlin.Any?): kotlin.Boolean declared in kotlin.internal.ir' type=kotlin.Boolean origin=EQEQ
|
||||
arg0: GET_VAR 'val tmp1_subject: kotlin.Int [val] declared in <root>.testComma' type=kotlin.Int origin=null
|
||||
arg1: CONST Int type=kotlin.Boolean value=1
|
||||
arg1: CONST Int type=kotlin.Int value=1
|
||||
then: CONST Boolean type=kotlin.Boolean value=true
|
||||
BRANCH
|
||||
if: CONST Boolean type=kotlin.Boolean value=true
|
||||
then: CALL 'public final fun EQEQ (arg0: kotlin.Any?, arg1: kotlin.Any?): kotlin.Boolean declared in kotlin.internal.ir' type=kotlin.Boolean origin=EQEQ
|
||||
arg0: GET_VAR 'val tmp1_subject: kotlin.Int [val] declared in <root>.testComma' type=kotlin.Int origin=null
|
||||
arg1: CONST Int type=kotlin.Boolean value=2
|
||||
arg1: CONST Int type=kotlin.Int value=2
|
||||
then: CONST Boolean type=kotlin.Boolean value=true
|
||||
BRANCH
|
||||
if: CONST Boolean type=kotlin.Boolean value=true
|
||||
then: CALL 'public final fun EQEQ (arg0: kotlin.Any?, arg1: kotlin.Any?): kotlin.Boolean declared in kotlin.internal.ir' type=kotlin.Boolean origin=EQEQ
|
||||
arg0: GET_VAR 'val tmp1_subject: kotlin.Int [val] declared in <root>.testComma' type=kotlin.Int origin=null
|
||||
arg1: CONST Int type=kotlin.Boolean value=3
|
||||
arg1: CONST Int type=kotlin.Int value=3
|
||||
then: CONST Boolean type=kotlin.Boolean value=true
|
||||
BRANCH
|
||||
if: CONST Boolean type=kotlin.Boolean value=true
|
||||
then: CALL 'public final fun EQEQ (arg0: kotlin.Any?, arg1: kotlin.Any?): kotlin.Boolean declared in kotlin.internal.ir' type=kotlin.Boolean origin=EQEQ
|
||||
arg0: GET_VAR 'val tmp1_subject: kotlin.Int [val] declared in <root>.testComma' type=kotlin.Int origin=null
|
||||
arg1: CONST Int type=kotlin.Boolean value=4
|
||||
arg1: CONST Int type=kotlin.Int value=4
|
||||
then: CONST String type=kotlin.String value="1234"
|
||||
BRANCH
|
||||
if: WHEN type=kotlin.Boolean origin=OROR
|
||||
@@ -125,32 +125,32 @@ FILE fqName:<root> fileName:/when.kt
|
||||
BRANCH
|
||||
if: CALL 'public final fun EQEQ (arg0: kotlin.Any?, arg1: kotlin.Any?): kotlin.Boolean declared in kotlin.internal.ir' type=kotlin.Boolean origin=EQEQ
|
||||
arg0: GET_VAR 'val tmp1_subject: kotlin.Int [val] declared in <root>.testComma' type=kotlin.Int origin=null
|
||||
arg1: CONST Int type=kotlin.Boolean value=5
|
||||
arg1: CONST Int type=kotlin.Int value=5
|
||||
then: CONST Boolean type=kotlin.Boolean value=true
|
||||
BRANCH
|
||||
if: CONST Boolean type=kotlin.Boolean value=true
|
||||
then: CALL 'public final fun EQEQ (arg0: kotlin.Any?, arg1: kotlin.Any?): kotlin.Boolean declared in kotlin.internal.ir' type=kotlin.Boolean origin=EQEQ
|
||||
arg0: GET_VAR 'val tmp1_subject: kotlin.Int [val] declared in <root>.testComma' type=kotlin.Int origin=null
|
||||
arg1: CONST Int type=kotlin.Boolean value=6
|
||||
arg1: CONST Int type=kotlin.Int value=6
|
||||
then: CONST Boolean type=kotlin.Boolean value=true
|
||||
BRANCH
|
||||
if: CONST Boolean type=kotlin.Boolean value=true
|
||||
then: CALL 'public final fun EQEQ (arg0: kotlin.Any?, arg1: kotlin.Any?): kotlin.Boolean declared in kotlin.internal.ir' type=kotlin.Boolean origin=EQEQ
|
||||
arg0: GET_VAR 'val tmp1_subject: kotlin.Int [val] declared in <root>.testComma' type=kotlin.Int origin=null
|
||||
arg1: CONST Int type=kotlin.Boolean value=7
|
||||
arg1: CONST Int type=kotlin.Int value=7
|
||||
then: CONST String type=kotlin.String value="567"
|
||||
BRANCH
|
||||
if: WHEN type=kotlin.Boolean origin=OROR
|
||||
BRANCH
|
||||
if: CALL 'public final fun EQEQ (arg0: kotlin.Any?, arg1: kotlin.Any?): kotlin.Boolean declared in kotlin.internal.ir' type=kotlin.Boolean origin=EQEQ
|
||||
arg0: GET_VAR 'val tmp1_subject: kotlin.Int [val] declared in <root>.testComma' type=kotlin.Int origin=null
|
||||
arg1: CONST Int type=kotlin.Boolean value=8
|
||||
arg1: CONST Int type=kotlin.Int value=8
|
||||
then: CONST Boolean type=kotlin.Boolean value=true
|
||||
BRANCH
|
||||
if: CONST Boolean type=kotlin.Boolean value=true
|
||||
then: CALL 'public final fun EQEQ (arg0: kotlin.Any?, arg1: kotlin.Any?): kotlin.Boolean declared in kotlin.internal.ir' type=kotlin.Boolean origin=EQEQ
|
||||
arg0: GET_VAR 'val tmp1_subject: kotlin.Int [val] declared in <root>.testComma' type=kotlin.Int origin=null
|
||||
arg1: CONST Int type=kotlin.Boolean value=9
|
||||
arg1: CONST Int type=kotlin.Int value=9
|
||||
then: CONST String type=kotlin.String value="89"
|
||||
BRANCH
|
||||
if: CONST Boolean type=kotlin.Boolean value=true
|
||||
|
||||
@@ -4,10 +4,14 @@ FILE fqName:<root> fileName:/whileDoWhile.kt
|
||||
VAR name:x type:kotlin.Int [var]
|
||||
CONST Int type=kotlin.Int value=0
|
||||
WHILE label=null origin=WHILE_LOOP
|
||||
condition: ERROR_CALL 'Comparison of arguments with different types: kotlin/Int, kotlin/Unit' type=kotlin.Boolean
|
||||
condition: CALL 'public final fun less (arg0: kotlin.Int, arg1: kotlin.Int): kotlin.Boolean declared in kotlin.internal.ir' type=kotlin.Boolean origin=LT
|
||||
arg0: GET_VAR 'var x: kotlin.Int [var] declared in <root>.test' type=kotlin.Int origin=null
|
||||
arg1: CONST Int type=kotlin.Int value=0
|
||||
body: BLOCK type=kotlin.Unit origin=null
|
||||
WHILE label=null origin=WHILE_LOOP
|
||||
condition: ERROR_CALL 'Comparison of arguments with different types: kotlin/Int, kotlin/Unit' type=kotlin.Boolean
|
||||
condition: CALL 'public final fun less (arg0: kotlin.Int, arg1: kotlin.Int): kotlin.Boolean declared in kotlin.internal.ir' type=kotlin.Boolean origin=LT
|
||||
arg0: GET_VAR 'var x: kotlin.Int [var] declared in <root>.test' type=kotlin.Int origin=null
|
||||
arg1: CONST Int type=kotlin.Int value=5
|
||||
body: BLOCK type=kotlin.Int origin=null
|
||||
VAR name:<unary> type:kotlin.Int [val]
|
||||
GET_VAR 'var x: kotlin.Int [var] declared in <root>.test' type=kotlin.Int origin=null
|
||||
@@ -16,7 +20,9 @@ FILE fqName:<root> fileName:/whileDoWhile.kt
|
||||
$this: GET_VAR 'val <unary>: kotlin.Int [val] declared in <root>.test' type=kotlin.Int origin=null
|
||||
GET_VAR 'val <unary>: kotlin.Int [val] declared in <root>.test' type=kotlin.Int origin=null
|
||||
WHILE label=null origin=WHILE_LOOP
|
||||
condition: ERROR_CALL 'Comparison of arguments with different types: kotlin/Int, kotlin/Unit' type=kotlin.Boolean
|
||||
condition: CALL 'public final fun less (arg0: kotlin.Int, arg1: kotlin.Int): kotlin.Boolean declared in kotlin.internal.ir' type=kotlin.Boolean origin=LT
|
||||
arg0: GET_VAR 'var x: kotlin.Int [var] declared in <root>.test' type=kotlin.Int origin=null
|
||||
arg1: CONST Int type=kotlin.Int value=10
|
||||
body: BLOCK type=kotlin.Int origin=null
|
||||
VAR name:<unary> type:kotlin.Int [val]
|
||||
GET_VAR 'var x: kotlin.Int [var] declared in <root>.test' type=kotlin.Int origin=null
|
||||
@@ -26,7 +32,9 @@ FILE fqName:<root> fileName:/whileDoWhile.kt
|
||||
GET_VAR 'val <unary>: kotlin.Int [val] declared in <root>.test' type=kotlin.Int origin=null
|
||||
DO_WHILE label=null origin=DO_WHILE_LOOP
|
||||
body: BLOCK type=kotlin.Unit origin=null
|
||||
condition: ERROR_CALL 'Comparison of arguments with different types: kotlin/Int, kotlin/Unit' type=kotlin.Boolean
|
||||
condition: CALL 'public final fun less (arg0: kotlin.Int, arg1: kotlin.Int): kotlin.Boolean declared in kotlin.internal.ir' type=kotlin.Boolean origin=LT
|
||||
arg0: GET_VAR 'var x: kotlin.Int [var] declared in <root>.test' type=kotlin.Int origin=null
|
||||
arg1: CONST Int type=kotlin.Int value=0
|
||||
DO_WHILE label=null origin=DO_WHILE_LOOP
|
||||
body: BLOCK type=kotlin.Int origin=null
|
||||
VAR name:<unary> type:kotlin.Int [val]
|
||||
@@ -35,7 +43,9 @@ FILE fqName:<root> fileName:/whileDoWhile.kt
|
||||
CALL 'public final fun inc (): kotlin.Int declared in kotlin.Int' type=kotlin.Int origin=null
|
||||
$this: GET_VAR 'val <unary>: kotlin.Int [val] declared in <root>.test' type=kotlin.Int origin=null
|
||||
GET_VAR 'val <unary>: kotlin.Int [val] declared in <root>.test' type=kotlin.Int origin=null
|
||||
condition: ERROR_CALL 'Comparison of arguments with different types: kotlin/Int, kotlin/Unit' type=kotlin.Boolean
|
||||
condition: CALL 'public final fun less (arg0: kotlin.Int, arg1: kotlin.Int): kotlin.Boolean declared in kotlin.internal.ir' type=kotlin.Boolean origin=LT
|
||||
arg0: GET_VAR 'var x: kotlin.Int [var] declared in <root>.test' type=kotlin.Int origin=null
|
||||
arg1: CONST Int type=kotlin.Int value=15
|
||||
DO_WHILE label=null origin=DO_WHILE_LOOP
|
||||
body: BLOCK type=kotlin.Int origin=null
|
||||
VAR name:<unary> type:kotlin.Int [val]
|
||||
@@ -44,7 +54,9 @@ FILE fqName:<root> fileName:/whileDoWhile.kt
|
||||
CALL 'public final fun inc (): kotlin.Int declared in kotlin.Int' type=kotlin.Int origin=null
|
||||
$this: GET_VAR 'val <unary>: kotlin.Int [val] declared in <root>.test' type=kotlin.Int origin=null
|
||||
GET_VAR 'val <unary>: kotlin.Int [val] declared in <root>.test' type=kotlin.Int origin=null
|
||||
condition: ERROR_CALL 'Comparison of arguments with different types: kotlin/Int, kotlin/Unit' type=kotlin.Boolean
|
||||
condition: CALL 'public final fun less (arg0: kotlin.Int, arg1: kotlin.Int): kotlin.Boolean declared in kotlin.internal.ir' type=kotlin.Boolean origin=LT
|
||||
arg0: GET_VAR 'var x: kotlin.Int [var] declared in <root>.test' type=kotlin.Int origin=null
|
||||
arg1: CONST Int type=kotlin.Int value=20
|
||||
FUN name:testSmartcastInCondition visibility:public modality:FINAL <> () returnType:kotlin.Unit
|
||||
BLOCK_BODY
|
||||
VAR name:a type:kotlin.Any? [val]
|
||||
|
||||
Reference in New Issue
Block a user