From 7a1eb9214d06a1dee31a37b81b118fb80537ca96 Mon Sep 17 00:00:00 2001 From: Denis Zharkov Date: Mon, 16 Mar 2020 18:14:48 +0300 Subject: [PATCH] FIR: Fix resolution for lambda returning resolved qualifier --- .../fir/resolve/dfa/FirDataFlowAnalyzer.kt | 4 + .../fir/resolve/dfa/cfg/ControlFlowGraph.kt | 6 + .../dfa/cfg/ControlFlowGraphBuilder.kt | 4 + .../dfa/cfg/ControlFlowGraphNodeBuilder.kt | 3 + .../dfa/cfg/ControlFlowGraphRenderer.kt | 1 + .../FirExpressionsResolveTransformer.kt | 13 +- .../resolve/cfg/lambdaReturningObject.dot | 67 +++++ .../resolve/cfg/lambdaReturningObject.kt | 14 + .../resolve/cfg/lambdaReturningObject.txt | 22 ++ .../resolve/exhaustiveWhenAndDNNType.dot | 260 ++++++++++-------- .../fir/FirDiagnosticsTestGenerated.java | 5 + ...DiagnosticsWithLightTreeTestGenerated.java | 5 + 12 files changed, 279 insertions(+), 125 deletions(-) create mode 100644 compiler/fir/resolve/testData/resolve/cfg/lambdaReturningObject.dot create mode 100644 compiler/fir/resolve/testData/resolve/cfg/lambdaReturningObject.kt create mode 100644 compiler/fir/resolve/testData/resolve/cfg/lambdaReturningObject.txt diff --git a/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/resolve/dfa/FirDataFlowAnalyzer.kt b/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/resolve/dfa/FirDataFlowAnalyzer.kt index cccf5729183..01e7cdfb302 100644 --- a/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/resolve/dfa/FirDataFlowAnalyzer.kt +++ b/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/resolve/dfa/FirDataFlowAnalyzer.kt @@ -586,6 +586,10 @@ abstract class FirDataFlowAnalyzer( exitSafeCall(qualifiedAccessExpression) } + fun exitResolvedQualifierNode(resolvedQualifier: FirResolvedQualifier) { + graphBuilder.exitResolvedQualifierNode(resolvedQualifier).mergeIncomingFlow() + } + fun enterCall(functionCall: FirCall) { graphBuilder.enterCall(functionCall) } diff --git a/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/resolve/dfa/cfg/ControlFlowGraph.kt b/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/resolve/dfa/cfg/ControlFlowGraph.kt index 5ecfc1ebebf..cac00f9cb3e 100644 --- a/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/resolve/dfa/cfg/ControlFlowGraph.kt +++ b/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/resolve/dfa/cfg/ControlFlowGraph.kt @@ -202,6 +202,12 @@ class QualifiedAccessNode( level: Int, id: Int ) : CFGNode(owner, level, id) +class ResolvedQualifierNode( + owner: ControlFlowGraph, + override val fir: FirResolvedQualifier, + level: Int, id: Int +) : CFGNode(owner, level, id) + class FunctionCallNode( owner: ControlFlowGraph, override val fir: FirFunctionCall, diff --git a/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/resolve/dfa/cfg/ControlFlowGraphBuilder.kt b/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/resolve/dfa/cfg/ControlFlowGraphBuilder.kt index 12425fe76b4..aa85a75b5d7 100644 --- a/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/resolve/dfa/cfg/ControlFlowGraphBuilder.kt +++ b/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/resolve/dfa/cfg/ControlFlowGraphBuilder.kt @@ -621,6 +621,10 @@ class ControlFlowGraphBuilder { return node } + fun exitResolvedQualifierNode(resolvedQualifier: FirResolvedQualifier): ResolvedQualifierNode { + return createResolvedQualifierNode(resolvedQualifier).also(this::addNewSimpleNode) + } + fun enterCall(call: FirCall) { levelCounter++ } diff --git a/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/resolve/dfa/cfg/ControlFlowGraphNodeBuilder.kt b/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/resolve/dfa/cfg/ControlFlowGraphNodeBuilder.kt index 882c93218f8..e50e83af1c0 100644 --- a/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/resolve/dfa/cfg/ControlFlowGraphNodeBuilder.kt +++ b/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/resolve/dfa/cfg/ControlFlowGraphNodeBuilder.kt @@ -39,6 +39,9 @@ fun ControlFlowGraphBuilder.createCheckNotNullCallNode(fir: FirCheckNotNullCall) fun ControlFlowGraphBuilder.createQualifiedAccessNode(fir: FirQualifiedAccessExpression): QualifiedAccessNode = QualifiedAccessNode(graph, fir, levelCounter, createId()) +fun ControlFlowGraphBuilder.createResolvedQualifierNode(fir: FirResolvedQualifier): ResolvedQualifierNode = + ResolvedQualifierNode(graph, fir, levelCounter, createId()) + fun ControlFlowGraphBuilder.createBlockEnterNode(fir: FirBlock): BlockEnterNode = BlockEnterNode(graph, fir, levelCounter, createId()) fun ControlFlowGraphBuilder.createBlockExitNode(fir: FirBlock): BlockExitNode = BlockExitNode(graph, fir, levelCounter, createId()) diff --git a/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/resolve/dfa/cfg/ControlFlowGraphRenderer.kt b/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/resolve/dfa/cfg/ControlFlowGraphRenderer.kt index 78c5e4be762..765ab16dd8b 100644 --- a/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/resolve/dfa/cfg/ControlFlowGraphRenderer.kt +++ b/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/resolve/dfa/cfg/ControlFlowGraphRenderer.kt @@ -166,6 +166,7 @@ private fun CFGNode<*>.render(): String = is LoopExitNode -> "Exit ${fir.type()}loop" is QualifiedAccessNode -> "Access variable ${fir.calleeReference.render(CfgRenderMode)}" + is ResolvedQualifierNode -> "Access qualifier ${fir.classId}" is OperatorCallNode -> "Operator ${fir.operation.operator}" is ComparisonExpressionNode -> "Comparison ${fir.operation.operator}" is TypeOperatorCallNode -> "Type operator: \"${fir.render(CfgRenderMode)}\"" diff --git a/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/resolve/transformers/body/resolve/FirExpressionsResolveTransformer.kt b/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/resolve/transformers/body/resolve/FirExpressionsResolveTransformer.kt index 401501dd462..e7b5735855e 100644 --- a/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/resolve/transformers/body/resolve/FirExpressionsResolveTransformer.kt +++ b/compiler/fir/resolve/src/org/jetbrains/kotlin/fir/resolve/transformers/body/resolve/FirExpressionsResolveTransformer.kt @@ -137,10 +137,15 @@ class FirExpressionsResolveTransformer(transformer: FirBodyResolveTransformer) : } } } - if (result is FirQualifiedAccessExpression) { - dataFlowAnalyzer.enterQualifiedAccessExpression(result) - result = components.transformQualifiedAccessUsingSmartcastInfo(result) - dataFlowAnalyzer.exitQualifiedAccessExpression(result) + when (result) { + is FirQualifiedAccessExpression -> { + dataFlowAnalyzer.enterQualifiedAccessExpression(result) + result = components.transformQualifiedAccessUsingSmartcastInfo(result) + dataFlowAnalyzer.exitQualifiedAccessExpression(result) + } + is FirResolvedQualifier -> { + dataFlowAnalyzer.exitResolvedQualifierNode(result) + } } return result.compose() } diff --git a/compiler/fir/resolve/testData/resolve/cfg/lambdaReturningObject.dot b/compiler/fir/resolve/testData/resolve/cfg/lambdaReturningObject.dot new file mode 100644 index 00000000000..db91e5134b4 --- /dev/null +++ b/compiler/fir/resolve/testData/resolve/cfg/lambdaReturningObject.dot @@ -0,0 +1,67 @@ +digraph lambdaReturningObject_kt { + graph [nodesep=3] + node [shape=box penwidth=2] + edge [penwidth=2] + + subgraph cluster_0 { + color=red + 0 [label="Enter function bar" style="filled" fillcolor=red]; + 1 [label="Exit function bar" style="filled" fillcolor=red]; + } + + 0 -> {1}; + + subgraph cluster_1 { + color=red + 2 [label="Enter function " style="filled" fillcolor=red]; + 3 [label="Delegated constructor call: super()"]; + 4 [label="Exit function " style="filled" fillcolor=red]; + } + + 2 -> {3}; + 3 -> {4}; + + subgraph cluster_2 { + color=red + 5 [label="Enter function MyOut" style="filled" fillcolor=red]; + 6 [label="Function call: R|kotlin/TODO|()"]; + 7 [label="Stub" style="filled" fillcolor=gray]; + 8 [label="Jump: ^MyOut R|kotlin/TODO|()" style="filled" fillcolor=gray]; + 9 [label="Stub" style="filled" fillcolor=gray]; + 10 [label="Exit function MyOut" style="filled" fillcolor=red]; + } + + 5 -> {6}; + 6 -> {10}; + 6 -> {7} [style=dotted]; + 7 -> {8} [style=dotted]; + 8 -> {10 9} [style=dotted]; + 9 -> {10} [style=dotted]; + + subgraph cluster_3 { + color=red + 11 [label="Enter function foo" style="filled" fillcolor=red]; + 12 [label="Postponed enter to lambda"]; + 13 [label="Postponed exit from lambda"]; + 14 [label="Function call: R|/MyOut|(...)"]; + 15 [label="Function call: R|/bar|(...)"]; + 16 [label="Exit function foo" style="filled" fillcolor=red]; + } + + 11 -> {12}; + 12 -> {13 13} [color=green]; + 13 -> {14}; + 14 -> {15}; + 15 -> {16}; + + subgraph cluster_4 { + color=red + 17 [label="Enter function anonymousFunction" style="filled" fillcolor=red]; + 18 [label="Access qualifier /IrStarProjectionImpl"]; + 19 [label="Exit function anonymousFunction" style="filled" fillcolor=red]; + } + + 17 -> {18}; + 18 -> {19}; + +} diff --git a/compiler/fir/resolve/testData/resolve/cfg/lambdaReturningObject.kt b/compiler/fir/resolve/testData/resolve/cfg/lambdaReturningObject.kt new file mode 100644 index 00000000000..0cf43a7165a --- /dev/null +++ b/compiler/fir/resolve/testData/resolve/cfg/lambdaReturningObject.kt @@ -0,0 +1,14 @@ +// !DUMP_CFG + +interface Out +fun bar(arguments: Out) {} + +interface IrTypeArgument + +object IrStarProjectionImpl : IrTypeArgument + +fun MyOut(init: () -> T): Out = TODO() + +fun foo() { + bar(MyOut { IrStarProjectionImpl }) +} diff --git a/compiler/fir/resolve/testData/resolve/cfg/lambdaReturningObject.txt b/compiler/fir/resolve/testData/resolve/cfg/lambdaReturningObject.txt new file mode 100644 index 00000000000..faca78a7228 --- /dev/null +++ b/compiler/fir/resolve/testData/resolve/cfg/lambdaReturningObject.txt @@ -0,0 +1,22 @@ +FILE: lambdaReturningObject.kt + public abstract interface Out : R|kotlin/Any| { + } + public final fun bar(arguments: R|Out|): R|kotlin/Unit| { + } + public abstract interface IrTypeArgument : R|kotlin/Any| { + } + public final object IrStarProjectionImpl : R|IrTypeArgument| { + private constructor(): R|IrStarProjectionImpl| { + super() + } + + } + public final fun MyOut(init: R|() -> T|): R|Out| { + ^MyOut R|kotlin/TODO|() + } + public final fun foo(): R|kotlin/Unit| { + R|/bar|(R|/MyOut|( = MyOut@fun (): R|IrStarProjectionImpl| { + ^ Q|IrStarProjectionImpl| + } + )) + } diff --git a/compiler/fir/resolve/testData/resolve/exhaustiveWhenAndDNNType.dot b/compiler/fir/resolve/testData/resolve/exhaustiveWhenAndDNNType.dot index 5a5b02b3403..732e6efea4c 100644 --- a/compiler/fir/resolve/testData/resolve/exhaustiveWhenAndDNNType.dot +++ b/compiler/fir/resolve/testData/resolve/exhaustiveWhenAndDNNType.dot @@ -50,49 +50,52 @@ digraph exhaustiveWhenAndDNNType_kt { subgraph cluster_5 { color=red 12 [label="Enter function test_1" style="filled" fillcolor=red]; - 13 [label="Access variable R|/SomeEnum.A1|"]; - 14 [label="Variable declaration: lval flag: R|SomeEnum|"]; + 13 [label="Access qualifier /SomeEnum"]; + 14 [label="Access variable R|/SomeEnum.A1|"]; + 15 [label="Variable declaration: lval flag: R|SomeEnum|"]; subgraph cluster_6 { color=blue - 15 [label="Enter when"]; - 16 [label="Access variable R|/flag|"]; - 17 [label="Check not null: R|/flag|!!"]; + 16 [label="Enter when"]; + 17 [label="Access variable R|/flag|"]; + 18 [label="Check not null: R|/flag|!!"]; subgraph cluster_7 { color=blue - 18 [label="Enter when branch condition "]; - 19 [label="Access variable R|/SomeEnum.A1|"]; - 20 [label="Operator =="]; - 21 [label="Exit when branch condition"]; + 19 [label="Enter when branch condition "]; + 20 [label="Access qualifier /SomeEnum"]; + 21 [label="Access variable R|/SomeEnum.A1|"]; + 22 [label="Operator =="]; + 23 [label="Exit when branch condition"]; } subgraph cluster_8 { color=blue - 22 [label="Enter when branch condition "]; - 23 [label="Access variable R|/SomeEnum.A2|"]; - 24 [label="Operator =="]; - 25 [label="Exit when branch condition"]; + 24 [label="Enter when branch condition "]; + 25 [label="Access qualifier /SomeEnum"]; + 26 [label="Access variable R|/SomeEnum.A2|"]; + 27 [label="Operator =="]; + 28 [label="Exit when branch condition"]; } - 26 [label="Enter when branch result"]; + 29 [label="Enter when branch result"]; subgraph cluster_9 { color=blue - 27 [label="Enter block"]; - 28 [label="Function call: R|/B.B|()"]; - 29 [label="Exit block"]; + 30 [label="Enter block"]; + 31 [label="Function call: R|/B.B|()"]; + 32 [label="Exit block"]; } - 30 [label="Exit when branch result"]; - 31 [label="Enter when branch result"]; + 33 [label="Exit when branch result"]; + 34 [label="Enter when branch result"]; subgraph cluster_10 { color=blue - 32 [label="Enter block"]; - 33 [label="Function call: R|/B.B|()"]; - 34 [label="Exit block"]; + 35 [label="Enter block"]; + 36 [label="Function call: R|/B.B|()"]; + 37 [label="Exit block"]; } - 35 [label="Exit when branch result"]; - 36 [label="Exit when"]; + 38 [label="Exit when branch result"]; + 39 [label="Exit when"]; } - 37 [label="Variable declaration: lval b: R|B|"]; - 38 [label="Access variable R|/b|"]; - 39 [label="Function call: R|/takeB|(...)"]; - 40 [label="Exit function test_1" style="filled" fillcolor=red]; + 40 [label="Variable declaration: lval b: R|B|"]; + 41 [label="Access variable R|/b|"]; + 42 [label="Function call: R|/takeB|(...)"]; + 43 [label="Exit function test_1" style="filled" fillcolor=red]; } 12 -> {13}; @@ -104,159 +107,165 @@ digraph exhaustiveWhenAndDNNType_kt { 18 -> {19}; 19 -> {20}; 20 -> {21}; - 21 -> {31 22}; + 21 -> {22}; 22 -> {23}; - 23 -> {24}; + 23 -> {34 24}; 24 -> {25}; 25 -> {26}; 26 -> {27}; 27 -> {28}; 28 -> {29}; 29 -> {30}; - 30 -> {36}; + 30 -> {31}; 31 -> {32}; 32 -> {33}; - 33 -> {34}; + 33 -> {39}; 34 -> {35}; 35 -> {36}; 36 -> {37}; 37 -> {38}; 38 -> {39}; 39 -> {40}; + 40 -> {41}; + 41 -> {42}; + 42 -> {43}; subgraph cluster_11 { color=red - 41 [label="Enter function test_2" style="filled" fillcolor=red]; - 42 [label="Access variable R|/SomeEnum.A1|"]; - 43 [label="Variable declaration: lval flag: R|SomeEnum|"]; + 44 [label="Enter function test_2" style="filled" fillcolor=red]; + 45 [label="Access qualifier /SomeEnum"]; + 46 [label="Access variable R|/SomeEnum.A1|"]; + 47 [label="Variable declaration: lval flag: R|SomeEnum|"]; subgraph cluster_12 { color=blue - 44 [label="Enter when"]; - 45 [label="Access variable R|/flag|"]; - 46 [label="Check not null: R|/flag|!!"]; + 48 [label="Enter when"]; + 49 [label="Access variable R|/flag|"]; + 50 [label="Check not null: R|/flag|!!"]; subgraph cluster_13 { color=blue - 47 [label="Enter when branch condition "]; - 48 [label="Access variable R|/SomeEnum.A1|"]; - 49 [label="Operator =="]; - 50 [label="Exit when branch condition"]; + 51 [label="Enter when branch condition "]; + 52 [label="Access qualifier /SomeEnum"]; + 53 [label="Access variable R|/SomeEnum.A1|"]; + 54 [label="Operator =="]; + 55 [label="Exit when branch condition"]; } subgraph cluster_14 { color=blue - 51 [label="Enter when branch condition "]; - 52 [label="Access variable R|/SomeEnum.A2|"]; - 53 [label="Operator =="]; - 54 [label="Exit when branch condition"]; + 56 [label="Enter when branch condition "]; + 57 [label="Access qualifier /SomeEnum"]; + 58 [label="Access variable R|/SomeEnum.A2|"]; + 59 [label="Operator =="]; + 60 [label="Exit when branch condition"]; } - 55 [label="Enter when branch result"]; + 61 [label="Enter when branch result"]; subgraph cluster_15 { color=blue - 56 [label="Enter block"]; - 57 [label="Function call: R|/B.B|()"]; - 58 [label="Exit block"]; + 62 [label="Enter block"]; + 63 [label="Function call: R|/B.B|()"]; + 64 [label="Exit block"]; } - 59 [label="Exit when branch result"]; - 60 [label="Enter when branch result"]; + 65 [label="Exit when branch result"]; + 66 [label="Enter when branch result"]; subgraph cluster_16 { color=blue - 61 [label="Enter block"]; - 62 [label="Function call: R|/B.B|()"]; - 63 [label="Exit block"]; + 67 [label="Enter block"]; + 68 [label="Function call: R|/B.B|()"]; + 69 [label="Exit block"]; } - 64 [label="Exit when branch result"]; - 65 [label="Exit when"]; + 70 [label="Exit when branch result"]; + 71 [label="Exit when"]; } - 66 [label="Variable declaration: lval b: R|B|"]; - 67 [label="Access variable R|/b|"]; - 68 [label="Function call: R|/takeB|(...)"]; - 69 [label="Exit function test_2" style="filled" fillcolor=red]; + 72 [label="Variable declaration: lval b: R|B|"]; + 73 [label="Access variable R|/b|"]; + 74 [label="Function call: R|/takeB|(...)"]; + 75 [label="Exit function test_2" style="filled" fillcolor=red]; } - 41 -> {42}; - 42 -> {43}; - 43 -> {44}; 44 -> {45}; 45 -> {46}; 46 -> {47}; 47 -> {48}; 48 -> {49}; 49 -> {50}; - 50 -> {60 51}; + 50 -> {51}; 51 -> {52}; 52 -> {53}; 53 -> {54}; 54 -> {55}; - 55 -> {56}; + 55 -> {66 56}; 56 -> {57}; 57 -> {58}; 58 -> {59}; - 59 -> {65}; + 59 -> {60}; 60 -> {61}; 61 -> {62}; 62 -> {63}; 63 -> {64}; 64 -> {65}; - 65 -> {66}; + 65 -> {71}; 66 -> {67}; 67 -> {68}; 68 -> {69}; - - subgraph cluster_17 { - color=red - 70 [label="Enter function test_3" style="filled" fillcolor=red]; - 71 [label="Access variable R|/SomeEnum.A1|"]; - 72 [label="Variable declaration: lval flag: R|SomeEnum|"]; - subgraph cluster_18 { - color=blue - 73 [label="Enter when"]; - 74 [label="Access variable R|/flag|"]; - subgraph cluster_19 { - color=blue - 75 [label="Enter when branch condition "]; - 76 [label="Access variable R|/SomeEnum.A1|"]; - 77 [label="Operator =="]; - 78 [label="Exit when branch condition"]; - } - subgraph cluster_20 { - color=blue - 79 [label="Enter when branch condition "]; - 80 [label="Access variable R|/SomeEnum.A2|"]; - 81 [label="Operator =="]; - 82 [label="Exit when branch condition"]; - } - 83 [label="Enter when branch result"]; - subgraph cluster_21 { - color=blue - 84 [label="Enter block"]; - 85 [label="Function call: R|/B.B|()"]; - 86 [label="Exit block"]; - } - 87 [label="Exit when branch result"]; - 88 [label="Enter when branch result"]; - subgraph cluster_22 { - color=blue - 89 [label="Enter block"]; - 90 [label="Function call: R|/B.B|()"]; - 91 [label="Exit block"]; - } - 92 [label="Exit when branch result"]; - 93 [label="Exit when"]; - } - 94 [label="Variable declaration: lval b: R|B|"]; - 95 [label="Access variable R|/b|"]; - 96 [label="Function call: R|/takeB|(...)"]; - 97 [label="Exit function test_3" style="filled" fillcolor=red]; - } - + 69 -> {70}; 70 -> {71}; 71 -> {72}; 72 -> {73}; 73 -> {74}; 74 -> {75}; - 75 -> {76}; + + subgraph cluster_17 { + color=red + 76 [label="Enter function test_3" style="filled" fillcolor=red]; + 77 [label="Access qualifier /SomeEnum"]; + 78 [label="Access variable R|/SomeEnum.A1|"]; + 79 [label="Variable declaration: lval flag: R|SomeEnum|"]; + subgraph cluster_18 { + color=blue + 80 [label="Enter when"]; + 81 [label="Access variable R|/flag|"]; + subgraph cluster_19 { + color=blue + 82 [label="Enter when branch condition "]; + 83 [label="Access qualifier /SomeEnum"]; + 84 [label="Access variable R|/SomeEnum.A1|"]; + 85 [label="Operator =="]; + 86 [label="Exit when branch condition"]; + } + subgraph cluster_20 { + color=blue + 87 [label="Enter when branch condition "]; + 88 [label="Access qualifier /SomeEnum"]; + 89 [label="Access variable R|/SomeEnum.A2|"]; + 90 [label="Operator =="]; + 91 [label="Exit when branch condition"]; + } + 92 [label="Enter when branch result"]; + subgraph cluster_21 { + color=blue + 93 [label="Enter block"]; + 94 [label="Function call: R|/B.B|()"]; + 95 [label="Exit block"]; + } + 96 [label="Exit when branch result"]; + 97 [label="Enter when branch result"]; + subgraph cluster_22 { + color=blue + 98 [label="Enter block"]; + 99 [label="Function call: R|/B.B|()"]; + 100 [label="Exit block"]; + } + 101 [label="Exit when branch result"]; + 102 [label="Exit when"]; + } + 103 [label="Variable declaration: lval b: R|B|"]; + 104 [label="Access variable R|/b|"]; + 105 [label="Function call: R|/takeB|(...)"]; + 106 [label="Exit function test_3" style="filled" fillcolor=red]; + } + 76 -> {77}; 77 -> {78}; - 78 -> {88 79}; + 78 -> {79}; 79 -> {80}; 80 -> {81}; 81 -> {82}; @@ -264,8 +273,8 @@ digraph exhaustiveWhenAndDNNType_kt { 83 -> {84}; 84 -> {85}; 85 -> {86}; - 86 -> {87}; - 87 -> {93}; + 86 -> {97 87}; + 87 -> {88}; 88 -> {89}; 89 -> {90}; 90 -> {91}; @@ -274,6 +283,15 @@ digraph exhaustiveWhenAndDNNType_kt { 93 -> {94}; 94 -> {95}; 95 -> {96}; - 96 -> {97}; + 96 -> {102}; + 97 -> {98}; + 98 -> {99}; + 99 -> {100}; + 100 -> {101}; + 101 -> {102}; + 102 -> {103}; + 103 -> {104}; + 104 -> {105}; + 105 -> {106}; } diff --git a/compiler/fir/resolve/tests/org/jetbrains/kotlin/fir/FirDiagnosticsTestGenerated.java b/compiler/fir/resolve/tests/org/jetbrains/kotlin/fir/FirDiagnosticsTestGenerated.java index 65db06cfee0..34571679e31 100644 --- a/compiler/fir/resolve/tests/org/jetbrains/kotlin/fir/FirDiagnosticsTestGenerated.java +++ b/compiler/fir/resolve/tests/org/jetbrains/kotlin/fir/FirDiagnosticsTestGenerated.java @@ -606,6 +606,11 @@ public class FirDiagnosticsTestGenerated extends AbstractFirDiagnosticsTest { runTest("compiler/fir/resolve/testData/resolve/cfg/lambdaAsReturnOfLambda.kt"); } + @TestMetadata("lambdaReturningObject.kt") + public void testLambdaReturningObject() throws Exception { + runTest("compiler/fir/resolve/testData/resolve/cfg/lambdaReturningObject.kt"); + } + @TestMetadata("lambdas.kt") public void testLambdas() throws Exception { runTest("compiler/fir/resolve/testData/resolve/cfg/lambdas.kt"); diff --git a/compiler/fir/resolve/tests/org/jetbrains/kotlin/fir/FirDiagnosticsWithLightTreeTestGenerated.java b/compiler/fir/resolve/tests/org/jetbrains/kotlin/fir/FirDiagnosticsWithLightTreeTestGenerated.java index 278508815e2..75e15fbf89b 100644 --- a/compiler/fir/resolve/tests/org/jetbrains/kotlin/fir/FirDiagnosticsWithLightTreeTestGenerated.java +++ b/compiler/fir/resolve/tests/org/jetbrains/kotlin/fir/FirDiagnosticsWithLightTreeTestGenerated.java @@ -606,6 +606,11 @@ public class FirDiagnosticsWithLightTreeTestGenerated extends AbstractFirDiagnos runTest("compiler/fir/resolve/testData/resolve/cfg/lambdaAsReturnOfLambda.kt"); } + @TestMetadata("lambdaReturningObject.kt") + public void testLambdaReturningObject() throws Exception { + runTest("compiler/fir/resolve/testData/resolve/cfg/lambdaReturningObject.kt"); + } + @TestMetadata("lambdas.kt") public void testLambdas() throws Exception { runTest("compiler/fir/resolve/testData/resolve/cfg/lambdas.kt");