Fix for KT-9897: Cannot pop operand off an empty stack" with -= on ArrayList element
#KT-9897 Fixed
This commit is contained in:
@@ -835,7 +835,10 @@ public class AsmUtil {
|
||||
}
|
||||
|
||||
public static void dup(@NotNull InstructionAdapter v, @NotNull Type type) {
|
||||
int size = type.getSize();
|
||||
dup(v, type.getSize());
|
||||
}
|
||||
|
||||
private static void dup(@NotNull InstructionAdapter v, int size) {
|
||||
if (size == 2) {
|
||||
v.dup2();
|
||||
}
|
||||
@@ -847,6 +850,36 @@ public class AsmUtil {
|
||||
}
|
||||
}
|
||||
|
||||
public static void dup(@NotNull InstructionAdapter v, @NotNull Type topOfStack, @NotNull Type afterTop) {
|
||||
if (topOfStack.getSize() == 0 && afterTop.getSize() == 0) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (topOfStack.getSize() == 0) {
|
||||
dup(v, afterTop);
|
||||
}
|
||||
else if (afterTop.getSize() == 0) {
|
||||
dup(v, topOfStack);
|
||||
}
|
||||
else if (afterTop.getSize() == 1) {
|
||||
if (topOfStack.getSize() == 1) {
|
||||
dup(v, 2);
|
||||
}
|
||||
else {
|
||||
v.dup2X1();
|
||||
v.pop2();
|
||||
v.dupX2();
|
||||
v.dupX2();
|
||||
v.pop();
|
||||
v.dup2X1();
|
||||
}
|
||||
}
|
||||
else {
|
||||
//Note: it's possible to write dup3 and dup4
|
||||
throw new UnsupportedOperationException("Don't know how generate dup3/dup4 for: " + topOfStack + " and " + afterTop);
|
||||
}
|
||||
}
|
||||
|
||||
public static void writeKotlinSyntheticClassAnnotation(@NotNull ClassBuilder v, @NotNull GenerationState state) {
|
||||
AnnotationVisitor av = v.newAnnotation(asmDescByFqNameWithoutInnerClasses(KOTLIN_SYNTHETIC_CLASS), true);
|
||||
JvmCodegenUtil.writeAbiVersion(av);
|
||||
|
||||
@@ -771,12 +771,12 @@ public abstract class StackValue {
|
||||
private final boolean isGetter;
|
||||
private final ExpressionCodegen codegen;
|
||||
private final ArgumentGenerator argumentGenerator;
|
||||
final List<ResolvedValueArgument> valueArguments;
|
||||
private final List<ResolvedValueArgument> valueArguments;
|
||||
private final FrameMap frame;
|
||||
private final StackValue receiver;
|
||||
private final ResolvedCall<FunctionDescriptor> resolvedGetCall;
|
||||
private final ResolvedCall<FunctionDescriptor> resolvedSetCall;
|
||||
DefaultCallMask mask;
|
||||
private DefaultCallMask mask;
|
||||
|
||||
public CollectionElementReceiver(
|
||||
@NotNull Callable callable,
|
||||
@@ -1424,6 +1424,11 @@ public abstract class StackValue {
|
||||
currentExtensionReceiver
|
||||
.moveToTopOfStack(hasExtensionReceiver ? type : currentExtensionReceiver.type, v, dispatchReceiver.type.getSize());
|
||||
}
|
||||
|
||||
@Override
|
||||
public void dup(@NotNull InstructionAdapter v, boolean withReceiver) {
|
||||
AsmUtil.dup(v, extensionReceiver.type, dispatchReceiver.type);
|
||||
}
|
||||
}
|
||||
|
||||
public abstract static class StackValueWithSimpleReceiver extends StackValue {
|
||||
|
||||
@@ -0,0 +1,41 @@
|
||||
object Test {
|
||||
var z = "0"
|
||||
var l = 0L
|
||||
|
||||
fun changeObject(): String {
|
||||
"1".someProperty += 1
|
||||
return z
|
||||
}
|
||||
|
||||
fun changeLong(): Long {
|
||||
2L.someProperty -= 1
|
||||
return l
|
||||
}
|
||||
|
||||
var String.someProperty: Int
|
||||
get() {
|
||||
return this.length
|
||||
}
|
||||
set(left) {
|
||||
z += this + left
|
||||
}
|
||||
|
||||
var Long.someProperty: Long
|
||||
get() {
|
||||
return l
|
||||
}
|
||||
set(left) {
|
||||
l += this + left
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
fun box(): String {
|
||||
val changeObject = Test.changeObject()
|
||||
if (changeObject != "012") return "fail 1: $changeObject"
|
||||
|
||||
val changeLong = Test.changeLong()
|
||||
if (changeLong != 1L) return "fail 1: $changeLong"
|
||||
|
||||
return "OK"
|
||||
}
|
||||
@@ -0,0 +1,38 @@
|
||||
var z = "0"
|
||||
var l = 0L
|
||||
|
||||
fun changeObject(): String {
|
||||
"1".someProperty += 1
|
||||
return z
|
||||
}
|
||||
|
||||
fun changeLong(): Long {
|
||||
2L.someProperty -= 1
|
||||
return l
|
||||
}
|
||||
|
||||
var String.someProperty: Int
|
||||
get() {
|
||||
return this.length
|
||||
}
|
||||
set(left) {
|
||||
z += this + left
|
||||
}
|
||||
|
||||
var Long.someProperty: Long
|
||||
get() {
|
||||
return l
|
||||
}
|
||||
set(left) {
|
||||
l += this + left
|
||||
}
|
||||
|
||||
fun box(): String {
|
||||
val changeObject = changeObject()
|
||||
if (changeObject != "012") return "fail 1: $changeObject"
|
||||
|
||||
val changeLong = changeLong()
|
||||
if (changeLong != 1L) return "fail 1: $changeLong"
|
||||
|
||||
return "OK"
|
||||
}
|
||||
@@ -0,0 +1,41 @@
|
||||
object Test {
|
||||
var z = "0"
|
||||
var l = 0L
|
||||
|
||||
fun changeObject(): String {
|
||||
"1".someProperty += 1
|
||||
return z
|
||||
}
|
||||
|
||||
fun changeLong(): Long {
|
||||
2L.someProperty -= 1
|
||||
return l
|
||||
}
|
||||
|
||||
@JvmStatic var String.someProperty: Int
|
||||
get() {
|
||||
return this.length
|
||||
}
|
||||
set(left) {
|
||||
z += this + left
|
||||
}
|
||||
|
||||
@JvmStatic var Long.someProperty: Long
|
||||
get() {
|
||||
return l
|
||||
}
|
||||
set(left) {
|
||||
l += this + left
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
fun box(): String {
|
||||
val changeObject = Test.changeObject()
|
||||
if (changeObject != "012") return "fail 1: $changeObject"
|
||||
|
||||
val changeLong = Test.changeLong()
|
||||
if (changeLong != 1L) return "fail 1: $changeLong"
|
||||
|
||||
return "OK"
|
||||
}
|
||||
+12
@@ -3883,6 +3883,18 @@ public class BlackBoxCodegenTestGenerated extends AbstractBlackBoxCodegenTest {
|
||||
doTest(fileName);
|
||||
}
|
||||
|
||||
@TestMetadata("kt9897.kt")
|
||||
public void testKt9897() throws Exception {
|
||||
String fileName = KotlinTestUtils.navigationMetadata("compiler/testData/codegen/box/extensionProperties/kt9897.kt");
|
||||
doTest(fileName);
|
||||
}
|
||||
|
||||
@TestMetadata("kt9897_topLevel.kt")
|
||||
public void testKt9897_topLevel() throws Exception {
|
||||
String fileName = KotlinTestUtils.navigationMetadata("compiler/testData/codegen/box/extensionProperties/kt9897_topLevel.kt");
|
||||
doTest(fileName);
|
||||
}
|
||||
|
||||
@TestMetadata("topLevel.kt")
|
||||
public void testTopLevel() throws Exception {
|
||||
String fileName = KotlinTestUtils.navigationMetadata("compiler/testData/codegen/box/extensionProperties/topLevel.kt");
|
||||
|
||||
+6
@@ -2299,6 +2299,12 @@ public class BlackBoxWithStdlibCodegenTestGenerated extends AbstractBlackBoxCode
|
||||
doTestWithStdlib(fileName);
|
||||
}
|
||||
|
||||
@TestMetadata("kt9897_static.kt")
|
||||
public void testKt9897_static() throws Exception {
|
||||
String fileName = KotlinTestUtils.navigationMetadata("compiler/testData/codegen/boxWithStdlib/jvmStatic/kt9897_static.kt");
|
||||
doTestWithStdlib(fileName);
|
||||
}
|
||||
|
||||
@TestMetadata("postfixInc.kt")
|
||||
public void testPostfixInc() throws Exception {
|
||||
String fileName = KotlinTestUtils.navigationMetadata("compiler/testData/codegen/boxWithStdlib/jvmStatic/postfixInc.kt");
|
||||
|
||||
Reference in New Issue
Block a user