Properly lower ImplicitClassReceiver

This commit is contained in:
Michael Bogdanov
2016-10-13 10:21:14 +03:00
committed by Dmitry Petrov
parent a93f929615
commit 20c4f47253
8 changed files with 133 additions and 2 deletions
@@ -26,6 +26,7 @@ import org.jetbrains.kotlin.psi.psiUtil.endOffset
import org.jetbrains.kotlin.psi.psiUtil.startOffset
import org.jetbrains.kotlin.psi2ir.intermediate.*
import org.jetbrains.kotlin.resolve.BindingContext
import org.jetbrains.kotlin.resolve.DescriptorUtils
import org.jetbrains.kotlin.resolve.calls.callResolverUtil.getSuperCallExpression
import org.jetbrains.kotlin.resolve.calls.callUtil.isSafeCall
import org.jetbrains.kotlin.resolve.calls.model.*
@@ -42,8 +43,17 @@ fun StatementGenerator.generateReceiver(ktDefaultElement: KtElement, receiver: R
}
val receiverExpression = when (receiver) {
is ImplicitClassReceiver ->
IrGetValueImpl(ktDefaultElement.startOffset, ktDefaultElement.startOffset, receiver.classDescriptor.thisAsReceiverParameter)
is ImplicitClassReceiver -> {
if (receiver.classDescriptor.kind.isSingleton &&
this.scopeOwner != receiver.classDescriptor && //For anonymous initializers
this.scopeOwner.containingDeclaration != receiver.classDescriptor) {
IrGetObjectValueImpl(ktDefaultElement.startOffset, ktDefaultElement.endOffset, receiver.type,
receiver.classDescriptor)
}
else {
IrGetValueImpl(ktDefaultElement.startOffset, ktDefaultElement.endOffset, receiver.classDescriptor.thisAsReceiverParameter)
}
}
is ThisClassReceiver ->
generateThisOrSuperReceiver(receiver, receiver.classDescriptor)
is SuperCallReceiverValue ->
+11
View File
@@ -0,0 +1,11 @@
class Z {
fun test2() {
test()
}
companion object {
fun test() {}
}
}
+17
View File
@@ -0,0 +1,17 @@
FILE /companion.kt
CLASS CLASS Z
CONSTRUCTOR public constructor Z()
BLOCK_BODY
DELEGATING_CONSTRUCTOR_CALL 'constructor Any()'
INSTANCE_INITIALIZER_CALL classDescriptor='Z'
FUN public final fun test2(): kotlin.Unit
BLOCK_BODY
CALL 'test(): Unit' type=kotlin.Unit origin=null
$this: GET_OBJECT 'companion object of Z' type=Z.Companion
CLASS OBJECT companion object of Z
CONSTRUCTOR private constructor Companion()
BLOCK_BODY
DELEGATING_CONSTRUCTOR_CALL 'constructor Any()'
INSTANCE_INITIALIZER_CALL classDescriptor='companion object of Z'
FUN public final fun test(): kotlin.Unit
BLOCK_BODY
+11
View File
@@ -0,0 +1,11 @@
enum class Z {
ENTRY {
fun test() {}
class A {
fun test2() {
test()
}
}
}
}
+28
View File
@@ -0,0 +1,28 @@
FILE /enumEntry.kt
CLASS ENUM_CLASS Z
CONSTRUCTOR private constructor Z()
BLOCK_BODY
ENUM_CONSTRUCTOR_CALL 'constructor Enum(String, Int)'
INSTANCE_INITIALIZER_CALL classDescriptor='Z'
ENUM_ENTRY enum entry ENTRY
init: ENUM_CONSTRUCTOR_CALL 'constructor ENTRY()'
class: CLASS ENUM_ENTRY ENTRY
CONSTRUCTOR private constructor ENTRY()
BLOCK_BODY
ENUM_CONSTRUCTOR_CALL 'constructor Z()'
INSTANCE_INITIALIZER_CALL classDescriptor='ENTRY'
FUN public final fun test(): kotlin.Unit
BLOCK_BODY
CLASS CLASS A
CONSTRUCTOR public constructor A()
BLOCK_BODY
DELEGATING_CONSTRUCTOR_CALL 'constructor Any()'
INSTANCE_INITIALIZER_CALL classDescriptor='A'
FUN public final fun test2(): kotlin.Unit
BLOCK_BODY
CALL 'test(): Unit' type=kotlin.Unit origin=null
$this: GET_OBJECT 'ENTRY' type=Z.ENTRY
FUN ENUM_CLASS_SPECIAL_MEMBER public final fun values(): kotlin.Array<Z>
SYNTHETIC_BODY kind=ENUM_VALUES
FUN ENUM_CLASS_SPECIAL_MEMBER public final fun valueOf(value: kotlin.String): Z
SYNTHETIC_BODY kind=ENUM_VALUEOF
+10
View File
@@ -0,0 +1,10 @@
object Z {
fun test() {}
class A {
fun test2() {
test()
}
}
}
+17
View File
@@ -0,0 +1,17 @@
FILE /object.kt
CLASS OBJECT Z
CONSTRUCTOR private constructor Z()
BLOCK_BODY
DELEGATING_CONSTRUCTOR_CALL 'constructor Any()'
INSTANCE_INITIALIZER_CALL classDescriptor='Z'
FUN public final fun test(): kotlin.Unit
BLOCK_BODY
CLASS CLASS A
CONSTRUCTOR public constructor A()
BLOCK_BODY
DELEGATING_CONSTRUCTOR_CALL 'constructor Any()'
INSTANCE_INITIALIZER_CALL classDescriptor='A'
FUN public final fun test2(): kotlin.Unit
BLOCK_BODY
CALL 'test(): Unit' type=kotlin.Unit origin=null
$this: GET_OBJECT 'Z' type=Z
@@ -766,4 +766,31 @@ public class IrTextTestCaseGenerated extends AbstractIrTextTestCase {
doTest(fileName);
}
}
@TestMetadata("compiler/testData/ir/irText/singletons")
@TestDataPath("$PROJECT_ROOT")
@RunWith(JUnit3RunnerWithInners.class)
public static class Singletons extends AbstractIrTextTestCase {
public void testAllFilesPresentInSingletons() throws Exception {
KotlinTestUtils.assertAllTestsPresentByMetadata(this.getClass(), new File("compiler/testData/ir/irText/singletons"), Pattern.compile("^(.+)\\.kt$"), true);
}
@TestMetadata("companion.kt")
public void testCompanion() throws Exception {
String fileName = KotlinTestUtils.navigationMetadata("compiler/testData/ir/irText/singletons/companion.kt");
doTest(fileName);
}
@TestMetadata("enumEntry.kt")
public void testEnumEntry() throws Exception {
String fileName = KotlinTestUtils.navigationMetadata("compiler/testData/ir/irText/singletons/enumEntry.kt");
doTest(fileName);
}
@TestMetadata("object.kt")
public void testObject() throws Exception {
String fileName = KotlinTestUtils.navigationMetadata("compiler/testData/ir/irText/singletons/object.kt");
doTest(fileName);
}
}
}