CFA: No more UNRESOLVED_CALL for object / enum entry qualifiers
(cherry picked from commit 4b09de8)
This commit is contained in:
committed by
Mikhail Glukhikh
parent
962c2e5dd2
commit
b7ed68db05
+79
@@ -0,0 +1,79 @@
|
||||
== O ==
|
||||
object O {
|
||||
val y = 1
|
||||
}
|
||||
---------------------
|
||||
L0:
|
||||
1 <START>
|
||||
v(val y = 1)
|
||||
r(1) -> <v0>
|
||||
w(y|<v0>)
|
||||
L1:
|
||||
<END> NEXT:[<SINK>]
|
||||
error:
|
||||
<ERROR> PREV:[]
|
||||
sink:
|
||||
<SINK> PREV:[<ERROR>, <END>]
|
||||
=====================
|
||||
== E ==
|
||||
enum class E(val x: Int) {
|
||||
E1(0)
|
||||
}
|
||||
---------------------
|
||||
L0:
|
||||
1 <START>
|
||||
v(val x: Int)
|
||||
magic[FAKE_INITIALIZER](val x: Int) -> <v0>
|
||||
w(x|<v0>)
|
||||
L1:
|
||||
<END> NEXT:[<SINK>]
|
||||
error:
|
||||
<ERROR> PREV:[]
|
||||
sink:
|
||||
<SINK> PREV:[<ERROR>, <END>]
|
||||
=====================
|
||||
== C ==
|
||||
class C {
|
||||
companion object {
|
||||
val z = 2
|
||||
}
|
||||
}
|
||||
---------------------
|
||||
L0:
|
||||
1 <START>
|
||||
L1:
|
||||
<END> NEXT:[<SINK>]
|
||||
error:
|
||||
<ERROR> PREV:[]
|
||||
sink:
|
||||
<SINK> PREV:[<ERROR>, <END>]
|
||||
=====================
|
||||
== foo ==
|
||||
fun foo() = E1.x + O.y + C.z
|
||||
---------------------
|
||||
L0:
|
||||
1 <START>
|
||||
mark(E1.x)
|
||||
mark(E1)
|
||||
r(E1) -> <v0>
|
||||
r(x|<v0>) -> <v1>
|
||||
mark(O.y)
|
||||
mark(O)
|
||||
r(O) -> <v2>
|
||||
r(y|<v2>) -> <v3>
|
||||
mark(E1.x + O.y)
|
||||
call(E1.x + O.y, plus|<v1>, <v3>) -> <v4>
|
||||
mark(C.z)
|
||||
mark(C)
|
||||
r(C, Companion) -> <v5>
|
||||
r(z|<v5>) -> <v6>
|
||||
mark(E1.x + O.y + C.z)
|
||||
call(E1.x + O.y + C.z, plus|<v4>, <v6>) -> <v7>
|
||||
ret(*|<v7>) L1
|
||||
L1:
|
||||
<END> NEXT:[<SINK>]
|
||||
error:
|
||||
<ERROR> PREV:[]
|
||||
sink:
|
||||
<SINK> PREV:[<ERROR>, <END>]
|
||||
=====================
|
||||
@@ -0,0 +1,17 @@
|
||||
import E.E1
|
||||
|
||||
object O {
|
||||
val y = 1
|
||||
}
|
||||
|
||||
enum class E(val x: Int) {
|
||||
E1(0)
|
||||
}
|
||||
|
||||
class C {
|
||||
companion object {
|
||||
val z = 2
|
||||
}
|
||||
}
|
||||
|
||||
fun foo() = E1.x + O.y + C.z
|
||||
+37
@@ -0,0 +1,37 @@
|
||||
== O ==
|
||||
object O {
|
||||
val y = 1
|
||||
}
|
||||
---------------------
|
||||
1 <v0>: Int NEW: r(1) -> <v0>
|
||||
=====================
|
||||
== E ==
|
||||
enum class E(val x: Int) {
|
||||
E1(0)
|
||||
}
|
||||
---------------------
|
||||
<v0>: Int NEW: magic[FAKE_INITIALIZER](val x: Int) -> <v0>
|
||||
=====================
|
||||
== C ==
|
||||
class C {
|
||||
companion object {
|
||||
val z = 2
|
||||
}
|
||||
}
|
||||
---------------------
|
||||
=====================
|
||||
== foo ==
|
||||
fun foo() = E1.x + O.y + C.z
|
||||
---------------------
|
||||
E1 <v0>: E NEW: r(E1) -> <v0>
|
||||
x <v1>: Int NEW: r(x|<v0>) -> <v1>
|
||||
E1.x <v1>: Int COPY
|
||||
O <v2>: O NEW: r(O) -> <v2>
|
||||
y <v3>: Int NEW: r(y|<v2>) -> <v3>
|
||||
O.y <v3>: Int COPY
|
||||
E1.x + O.y <v4>: Int NEW: call(E1.x + O.y, plus|<v1>, <v3>) -> <v4>
|
||||
C <v5>: C.Companion NEW: r(C, Companion) -> <v5>
|
||||
z <v6>: Int NEW: r(z|<v5>) -> <v6>
|
||||
C.z <v6>: Int COPY
|
||||
E1.x + O.y + C.z <v7>: Int NEW: call(E1.x + O.y + C.z, plus|<v4>, <v6>) -> <v7>
|
||||
=====================
|
||||
Vendored
+171
@@ -0,0 +1,171 @@
|
||||
== A ==
|
||||
class A {
|
||||
companion object
|
||||
}
|
||||
---------------------
|
||||
L0:
|
||||
1 <START>
|
||||
L1:
|
||||
<END> NEXT:[<SINK>]
|
||||
error:
|
||||
<ERROR> PREV:[]
|
||||
sink:
|
||||
<SINK> PREV:[<ERROR>, <END>]
|
||||
=====================
|
||||
== B ==
|
||||
object B {
|
||||
val A.Companion.foo: X get() = X
|
||||
}
|
||||
---------------------
|
||||
L0:
|
||||
1 <START>
|
||||
v(val A.Companion.foo: X get() = X)
|
||||
L1:
|
||||
<END> NEXT:[<SINK>]
|
||||
error:
|
||||
<ERROR> PREV:[]
|
||||
sink:
|
||||
<SINK> PREV:[<ERROR>, <END>]
|
||||
=====================
|
||||
== X ==
|
||||
object X
|
||||
---------------------
|
||||
L0:
|
||||
1 <START>
|
||||
L1:
|
||||
<END> NEXT:[<SINK>]
|
||||
error:
|
||||
<ERROR> PREV:[]
|
||||
sink:
|
||||
<SINK> PREV:[<ERROR>, <END>]
|
||||
=====================
|
||||
== C ==
|
||||
object C {
|
||||
operator fun X.invoke() = println("Hello!")
|
||||
}
|
||||
---------------------
|
||||
L0:
|
||||
1 <START>
|
||||
L1:
|
||||
<END> NEXT:[<SINK>]
|
||||
error:
|
||||
<ERROR> PREV:[]
|
||||
sink:
|
||||
<SINK> PREV:[<ERROR>, <END>]
|
||||
=====================
|
||||
== invoke ==
|
||||
operator fun X.invoke() = println("Hello!")
|
||||
---------------------
|
||||
L0:
|
||||
1 <START>
|
||||
mark("Hello!")
|
||||
r("Hello!") -> <v0>
|
||||
mark(println("Hello!"))
|
||||
magic[UNRESOLVED_CALL](println("Hello!")|<v0>, !<v1>) -> <v2>
|
||||
ret(*|<v2>) L1
|
||||
L1:
|
||||
<END> NEXT:[<SINK>]
|
||||
error:
|
||||
<ERROR> PREV:[]
|
||||
sink:
|
||||
<SINK> PREV:[<ERROR>, <END>]
|
||||
=====================
|
||||
== with ==
|
||||
inline fun <T, R> with(receiver: T, block: T.() -> R): R = receiver.block()
|
||||
---------------------
|
||||
L0:
|
||||
1 <START>
|
||||
v(receiver: T)
|
||||
magic[FAKE_INITIALIZER](receiver: T) -> <v0>
|
||||
w(receiver|<v0>)
|
||||
v(block: T.() -> R)
|
||||
magic[FAKE_INITIALIZER](block: T.() -> R) -> <v1>
|
||||
w(block|<v1>)
|
||||
mark(receiver.block())
|
||||
r(block) -> <v2>
|
||||
r(receiver) -> <v3>
|
||||
mark(block())
|
||||
call(block(), invoke|<v2>, <v3>) -> <v4>
|
||||
ret(*|<v4>) L1
|
||||
L1:
|
||||
<END> NEXT:[<SINK>]
|
||||
error:
|
||||
<ERROR> PREV:[]
|
||||
sink:
|
||||
<SINK> PREV:[<ERROR>, <END>]
|
||||
=====================
|
||||
== use ==
|
||||
fun use() = with(C) {
|
||||
with(B) {
|
||||
A.foo()
|
||||
}
|
||||
}
|
||||
---------------------
|
||||
L0:
|
||||
1 <START>
|
||||
r(C) -> <v0>
|
||||
mark({ with(B) { A.foo() } })
|
||||
jmp?(L2) NEXT:[r({ with(B) { A.foo() } }) -> <v1>, d({ with(B) { A.foo() } })]
|
||||
d({ with(B) { A.foo() } }) NEXT:[<SINK>]
|
||||
L2 [after local declaration]:
|
||||
r({ with(B) { A.foo() } }) -> <v1> PREV:[jmp?(L2)]
|
||||
mark(with(C) { with(B) { A.foo() } })
|
||||
call(with(C) { with(B) { A.foo() } }, with|<v0>, <v1>) -> <v2>
|
||||
ret(*|<v2>) L1
|
||||
L1:
|
||||
<END> NEXT:[<SINK>]
|
||||
error:
|
||||
<ERROR> PREV:[]
|
||||
sink:
|
||||
<SINK> PREV:[<ERROR>, <END>, d({ with(B) { A.foo() } })]
|
||||
=====================
|
||||
== anonymous_0 ==
|
||||
{
|
||||
with(B) {
|
||||
A.foo()
|
||||
}
|
||||
}
|
||||
---------------------
|
||||
L3:
|
||||
2 <START>
|
||||
3 mark(with(B) { A.foo() })
|
||||
r(B) -> <v0>
|
||||
mark({ A.foo() })
|
||||
jmp?(L5) NEXT:[r({ A.foo() }) -> <v1>, d({ A.foo() })]
|
||||
d({ A.foo() }) NEXT:[<SINK>]
|
||||
L5 [after local declaration]:
|
||||
r({ A.foo() }) -> <v1> PREV:[jmp?(L5)]
|
||||
mark(with(B) { A.foo() })
|
||||
call(with(B) { A.foo() }, with|<v0>, <v1>) -> <v2>
|
||||
2 ret(*|<v2>) L4
|
||||
L4:
|
||||
<END> NEXT:[<SINK>]
|
||||
error:
|
||||
<ERROR> PREV:[]
|
||||
sink:
|
||||
<SINK> PREV:[<ERROR>, <END>, d({ A.foo() })]
|
||||
=====================
|
||||
== anonymous_1 ==
|
||||
{
|
||||
A.foo()
|
||||
}
|
||||
---------------------
|
||||
L6:
|
||||
4 <START>
|
||||
5 mark(A.foo())
|
||||
mark(A.foo())
|
||||
magic[IMPLICIT_RECEIVER](foo) -> <v0>
|
||||
mark(A)
|
||||
r(A, Companion) -> <v1>
|
||||
r(foo|<v0>, <v1>) -> <v2>
|
||||
magic[IMPLICIT_RECEIVER](foo()) -> <v3>
|
||||
mark(foo())
|
||||
call(foo(), invoke|<v2>, <v3>) -> <v4>
|
||||
4 ret(*|<v4>) L7
|
||||
L7:
|
||||
<END> NEXT:[<SINK>]
|
||||
error:
|
||||
<ERROR> PREV:[]
|
||||
sink:
|
||||
<SINK> PREV:[<ERROR>, <END>]
|
||||
=====================
|
||||
+21
@@ -0,0 +1,21 @@
|
||||
class A {
|
||||
companion object
|
||||
}
|
||||
|
||||
object B {
|
||||
val A.Companion.foo: X get() = X
|
||||
}
|
||||
|
||||
object X
|
||||
|
||||
object C {
|
||||
operator fun X.invoke() = println("Hello!")
|
||||
}
|
||||
|
||||
inline fun <T, R> with(receiver: T, block: T.() -> R): R = receiver.block()
|
||||
|
||||
fun use() = with(C) {
|
||||
with(B) {
|
||||
A.foo()
|
||||
}
|
||||
}
|
||||
+75
@@ -0,0 +1,75 @@
|
||||
== A ==
|
||||
class A {
|
||||
companion object
|
||||
}
|
||||
---------------------
|
||||
=====================
|
||||
== B ==
|
||||
object B {
|
||||
val A.Companion.foo: X get() = X
|
||||
}
|
||||
---------------------
|
||||
=====================
|
||||
== X ==
|
||||
object X
|
||||
---------------------
|
||||
=====================
|
||||
== C ==
|
||||
object C {
|
||||
operator fun X.invoke() = println("Hello!")
|
||||
}
|
||||
---------------------
|
||||
=====================
|
||||
== invoke ==
|
||||
operator fun X.invoke() = println("Hello!")
|
||||
---------------------
|
||||
println !<v1>: *
|
||||
"Hello!" <v0>: * NEW: r("Hello!") -> <v0>
|
||||
println("Hello!") <v2>: {<: [ERROR : Error function type]} NEW: magic[UNRESOLVED_CALL](println("Hello!")|<v0>, !<v1>) -> <v2>
|
||||
=====================
|
||||
== with ==
|
||||
inline fun <T, R> with(receiver: T, block: T.() -> R): R = receiver.block()
|
||||
---------------------
|
||||
<v0>: {<: T} NEW: magic[FAKE_INITIALIZER](receiver: T) -> <v0>
|
||||
<v1>: {<: T.() -> R} NEW: magic[FAKE_INITIALIZER](block: T.() -> R) -> <v1>
|
||||
receiver <v3>: {<: T} NEW: r(receiver) -> <v3>
|
||||
block <v2>: {<: (T) -> R} NEW: r(block) -> <v2>
|
||||
block() <v4>: {<: R} NEW: call(block(), invoke|<v2>, <v3>) -> <v4>
|
||||
receiver.block() <v4>: {<: R} COPY
|
||||
=====================
|
||||
== use ==
|
||||
fun use() = with(C) {
|
||||
with(B) {
|
||||
A.foo()
|
||||
}
|
||||
}
|
||||
---------------------
|
||||
C <v0>: C NEW: r(C) -> <v0>
|
||||
{ with(B) { A.foo() } } <v1>: {<: C.() -> ???} NEW: r({ with(B) { A.foo() } }) -> <v1>
|
||||
with(C) { with(B) { A.foo() } } <v2>: {<: [ERROR : Error function type]} NEW: call(with(C) { with(B) { A.foo() } }, with|<v0>, <v1>) -> <v2>
|
||||
=====================
|
||||
== anonymous_0 ==
|
||||
{
|
||||
with(B) {
|
||||
A.foo()
|
||||
}
|
||||
}
|
||||
---------------------
|
||||
B <v0>: B NEW: r(B) -> <v0>
|
||||
{ A.foo() } <v1>: {<: B.() -> ???} NEW: r({ A.foo() }) -> <v1>
|
||||
with(B) { A.foo() } <v2>: {<: ???} NEW: call(with(B) { A.foo() }, with|<v0>, <v1>) -> <v2>
|
||||
with(B) { A.foo() } <v2>: {<: ???} COPY
|
||||
=====================
|
||||
== anonymous_1 ==
|
||||
{
|
||||
A.foo()
|
||||
}
|
||||
---------------------
|
||||
<v0>: B NEW: magic[IMPLICIT_RECEIVER](foo) -> <v0>
|
||||
<v3>: C NEW: magic[IMPLICIT_RECEIVER](foo()) -> <v3>
|
||||
A <v1>: A.Companion NEW: r(A, Companion) -> <v1>
|
||||
foo <v2>: X NEW: r(foo|<v0>, <v1>) -> <v2>
|
||||
foo() <v4>: {<: [ERROR : Error function type]} NEW: call(foo(), invoke|<v2>, <v3>) -> <v4>
|
||||
A.foo() <v4>: {<: [ERROR : Error function type]} COPY
|
||||
A.foo() <v4>: {<: [ERROR : Error function type]} COPY
|
||||
=====================
|
||||
Reference in New Issue
Block a user