|
@@ -17,6 +17,7 @@ import org.openzen.zenscript.codemodel.type.storage.StorageTag;
|
17
|
17
|
import org.openzen.zenscript.codemodel.type.storage.UniqueStorageTag;
|
18
|
18
|
import org.openzen.zenscript.javabytecode.JavaBytecodeContext;
|
19
|
19
|
import org.openzen.zenscript.javabytecode.JavaLocalVariableInfo;
|
|
20
|
+import org.openzen.zenscript.javabytecode.compiler.JavaModificationExpressionVisitor.PushOption;
|
20
|
21
|
import org.openzen.zenscript.javashared.*;
|
21
|
22
|
|
22
|
23
|
import java.io.FileOutputStream;
|
|
@@ -26,7 +27,6 @@ import java.util.Arrays;
|
26
|
27
|
import java.util.Comparator;
|
27
|
28
|
import java.util.Objects;
|
28
|
29
|
import java.util.StringJoiner;
|
29
|
|
-import org.openzen.zenscript.javabytecode.compiler.JavaModificationExpressionVisitor.PushOption;
|
30
|
30
|
|
31
|
31
|
public class JavaExpressionVisitor implements ExpressionVisitor<Void>, JavaNativeTranslator<Void> {
|
32
|
32
|
private static final JavaMethod BOOLEAN_PARSE = JavaMethod.getNativeStatic(JavaClass.BOOLEAN, "parseBoolean", "(Ljava/lang/String;)Z");
|
|
@@ -392,6 +392,7 @@ public class JavaExpressionVisitor implements ExpressionVisitor<Void>, JavaNativ
|
392
|
392
|
case STRING_RANGEGET:
|
393
|
393
|
case ARRAY_INDEXGETRANGE:
|
394
|
394
|
case ARRAY_INDEXGET:
|
|
395
|
+ case ARRAY_CONTAINS:
|
395
|
396
|
break;
|
396
|
397
|
case BYTE_INC:
|
397
|
398
|
modify(expression.target, () -> {
|
|
@@ -457,7 +458,7 @@ public class JavaExpressionVisitor implements ExpressionVisitor<Void>, JavaNativ
|
457
|
458
|
case UINT_INC:
|
458
|
459
|
case USIZE_INC:
|
459
|
460
|
if (expression.target instanceof GetLocalVariableExpression) {
|
460
|
|
- JavaLocalVariableInfo local = javaWriter.getLocalVariable(((GetLocalVariableExpression)expression.target).variable.variable);
|
|
461
|
+ JavaLocalVariableInfo local = javaWriter.getLocalVariable(((GetLocalVariableExpression) expression.target).variable.variable);
|
461
|
462
|
javaWriter.iinc(local.local);
|
462
|
463
|
javaWriter.load(local);
|
463
|
464
|
} else {
|
|
@@ -471,7 +472,7 @@ public class JavaExpressionVisitor implements ExpressionVisitor<Void>, JavaNativ
|
471
|
472
|
case UINT_DEC:
|
472
|
473
|
case USIZE_DEC:
|
473
|
474
|
if (expression.target instanceof GetLocalVariableExpression) {
|
474
|
|
- JavaLocalVariableInfo local = javaWriter.getLocalVariable(((GetLocalVariableExpression)expression.target).variable.variable);
|
|
475
|
+ JavaLocalVariableInfo local = javaWriter.getLocalVariable(((GetLocalVariableExpression) expression.target).variable.variable);
|
475
|
476
|
javaWriter.iinc(local.local, -1);
|
476
|
477
|
javaWriter.load(local);
|
477
|
478
|
} else {
|
|
@@ -525,7 +526,7 @@ public class JavaExpressionVisitor implements ExpressionVisitor<Void>, JavaNativ
|
525
|
526
|
final Label isFalse = new Label();
|
526
|
527
|
final Label end = new Label();
|
527
|
528
|
|
528
|
|
- if(builtin == BuiltinID.OPTIONAL_IS_NULL)
|
|
529
|
+ if (builtin == BuiltinID.OPTIONAL_IS_NULL)
|
529
|
530
|
javaWriter.ifNonNull(isFalse);
|
530
|
531
|
else
|
531
|
532
|
javaWriter.ifNull(isFalse);
|
|
@@ -995,7 +996,64 @@ public class JavaExpressionVisitor implements ExpressionVisitor<Void>, JavaNativ
|
995
|
996
|
break;
|
996
|
997
|
}
|
997
|
998
|
case ARRAY_CONTAINS:
|
998
|
|
- throw new UnsupportedOperationException("Not yet supported!");
|
|
999
|
+ expression.target.accept(this);
|
|
1000
|
+ final Label loopStart = new Label();
|
|
1001
|
+ final Label loopEnd = new Label();
|
|
1002
|
+ final Label isTrue = new Label();
|
|
1003
|
+ final Label expressionEnd = new Label();
|
|
1004
|
+
|
|
1005
|
+ final int counterLocation = javaWriter.local(int.class);
|
|
1006
|
+ javaWriter.iConst0();
|
|
1007
|
+ javaWriter.storeInt(counterLocation);
|
|
1008
|
+
|
|
1009
|
+ javaWriter.label(loopStart);
|
|
1010
|
+ javaWriter.dup();
|
|
1011
|
+ javaWriter.arrayLength();
|
|
1012
|
+
|
|
1013
|
+ javaWriter.loadInt(counterLocation);
|
|
1014
|
+
|
|
1015
|
+ javaWriter.ifICmpLE(loopEnd);
|
|
1016
|
+ javaWriter.dup();
|
|
1017
|
+ javaWriter.loadInt(counterLocation);
|
|
1018
|
+ final StoredType itemType = expression.arguments.arguments[0].type;
|
|
1019
|
+ javaWriter.arrayLoad(context.getType(itemType));
|
|
1020
|
+ javaWriter.iinc(counterLocation);
|
|
1021
|
+ expression.arguments.arguments[0].accept(this);
|
|
1022
|
+
|
|
1023
|
+
|
|
1024
|
+ if (CompilerUtils.isPrimitive(itemType.type)) {
|
|
1025
|
+ //Compare non-int types beforehand
|
|
1026
|
+ if (itemType.type == BasicTypeID.LONG || itemType.type == BasicTypeID.ULONG) {
|
|
1027
|
+ javaWriter.lCmp();
|
|
1028
|
+ javaWriter.ifNE(loopStart);
|
|
1029
|
+ } else if (itemType.type == BasicTypeID.FLOAT) {
|
|
1030
|
+ javaWriter.fCmp();
|
|
1031
|
+ javaWriter.ifNE(loopStart);
|
|
1032
|
+ } else if (itemType.type == BasicTypeID.DOUBLE) {
|
|
1033
|
+ javaWriter.dCmp();
|
|
1034
|
+ javaWriter.ifNE(loopStart);
|
|
1035
|
+ } else
|
|
1036
|
+ javaWriter.ifICmpNE(loopStart);
|
|
1037
|
+ } else {
|
|
1038
|
+ //If equals, use Object.equals in case of null
|
|
1039
|
+ javaWriter.invokeStatic(new JavaMethod(JavaClass.fromInternalName("java/util/Objects", JavaClass.Kind.CLASS), JavaMethod.Kind.STATIC, "equals", false, "(Ljava/lang/Object;Ljava/lang/Object;)Z", 0, false));
|
|
1040
|
+ javaWriter.ifNE(loopStart);
|
|
1041
|
+ // If ==
|
|
1042
|
+ // javaWriter.ifACmpNe(loopStart);
|
|
1043
|
+ }
|
|
1044
|
+
|
|
1045
|
+ javaWriter.label(isTrue);
|
|
1046
|
+
|
|
1047
|
+ javaWriter.pop();
|
|
1048
|
+ javaWriter.iConst1();
|
|
1049
|
+ javaWriter.goTo(expressionEnd);
|
|
1050
|
+
|
|
1051
|
+ javaWriter.label(loopEnd);
|
|
1052
|
+ javaWriter.pop();
|
|
1053
|
+ javaWriter.iConst0();
|
|
1054
|
+ javaWriter.label(expressionEnd);
|
|
1055
|
+
|
|
1056
|
+ break;
|
999
|
1057
|
case ARRAY_EQUALS:
|
1000
|
1058
|
case ARRAY_NOTEQUALS: {
|
1001
|
1059
|
ArrayTypeID type = (ArrayTypeID) expression.target.type.type;
|
|
@@ -3459,7 +3517,7 @@ public class JavaExpressionVisitor implements ExpressionVisitor<Void>, JavaNativ
|
3459
|
3517
|
javaWriter.aThrow();
|
3460
|
3518
|
return null;
|
3461
|
3519
|
}
|
3462
|
|
-
|
|
3520
|
+
|
3463
|
3521
|
private void modify(Expression source, Runnable modification, PushOption push) {
|
3464
|
3522
|
source.accept(new JavaModificationExpressionVisitor(context, module, javaWriter, this, modification, push));
|
3465
|
3523
|
}
|
|
@@ -3532,7 +3590,7 @@ public class JavaExpressionVisitor implements ExpressionVisitor<Void>, JavaNativ
|
3532
|
3590
|
case UINT_INC:
|
3533
|
3591
|
case USIZE_INC:
|
3534
|
3592
|
if (expression.target instanceof GetLocalVariableExpression) {
|
3535
|
|
- JavaLocalVariableInfo local = javaWriter.getLocalVariable(((GetLocalVariableExpression)expression.target).variable.variable);
|
|
3593
|
+ JavaLocalVariableInfo local = javaWriter.getLocalVariable(((GetLocalVariableExpression) expression.target).variable.variable);
|
3536
|
3594
|
javaWriter.load(local);
|
3537
|
3595
|
javaWriter.iinc(local.local);
|
3538
|
3596
|
} else {
|
|
@@ -3546,7 +3604,7 @@ public class JavaExpressionVisitor implements ExpressionVisitor<Void>, JavaNativ
|
3546
|
3604
|
case UINT_DEC:
|
3547
|
3605
|
case USIZE_DEC:
|
3548
|
3606
|
if (expression.target instanceof GetLocalVariableExpression) {
|
3549
|
|
- JavaLocalVariableInfo local = javaWriter.getLocalVariable(((GetLocalVariableExpression)expression.target).variable.variable);
|
|
3607
|
+ JavaLocalVariableInfo local = javaWriter.getLocalVariable(((GetLocalVariableExpression) expression.target).variable.variable);
|
3550
|
3608
|
javaWriter.load(local);
|
3551
|
3609
|
javaWriter.iinc(local.local, -1);
|
3552
|
3610
|
} else {
|
|
@@ -3598,12 +3656,12 @@ public class JavaExpressionVisitor implements ExpressionVisitor<Void>, JavaNativ
|
3598
|
3656
|
throw new IllegalArgumentException("Unknown postcall builtin: " + expression.member.getBuiltin());
|
3599
|
3657
|
}
|
3600
|
3658
|
}
|
3601
|
|
-
|
|
3659
|
+
|
3602
|
3660
|
modify(expression.target, () -> {
|
3603
|
3661
|
if (!checkAndExecuteMethodInfo(expression.member, expression.type, expression))
|
3604
|
3662
|
throw new IllegalStateException("Call target has no method info!");
|
3605
|
3663
|
}, PushOption.BEFORE);
|
3606
|
|
-
|
|
3664
|
+
|
3607
|
3665
|
return null;
|
3608
|
3666
|
}
|
3609
|
3667
|
|
|
@@ -3694,7 +3752,7 @@ public class JavaExpressionVisitor implements ExpressionVisitor<Void>, JavaNativ
|
3694
|
3752
|
javaWriter.getStaticField(context.getJavaField(expression.getter));
|
3695
|
3753
|
return null;
|
3696
|
3754
|
}
|
3697
|
|
-
|
|
3755
|
+
|
3698
|
3756
|
if (!checkAndExecuteMethodInfo(expression.getter, expression.type, expression))
|
3699
|
3757
|
throw new IllegalStateException("Call target has no method info!");
|
3700
|
3758
|
|
|
@@ -3876,7 +3934,7 @@ public class JavaExpressionVisitor implements ExpressionVisitor<Void>, JavaNativ
|
3876
|
3934
|
|
3877
|
3935
|
//Will return true if a JavaMethodInfo.class tag exists, and will compile that tag
|
3878
|
3936
|
@SuppressWarnings({"Raw", "unchecked"})
|
3879
|
|
- private boolean checkAndExecuteMethodInfo(DefinitionMemberRef member, StoredType resultType, Expression expression) {
|
|
3937
|
+ boolean checkAndExecuteMethodInfo(DefinitionMemberRef member, StoredType resultType, Expression expression) {
|
3880
|
3938
|
JavaMethod methodInfo = context.getJavaMethod(member);
|
3881
|
3939
|
if (methodInfo == null)
|
3882
|
3940
|
return false;
|