Selaa lähdekoodia

- Changed the way static is determined in an expression writer

- Minor code improvements; make better use of JavaMethodInfo
Stan Hebben 6 vuotta sitten
vanhempi
commit
3ef3a8d6cf

+ 10
- 10
JavaBytecodeCompiler/src/main/java/org/openzen/zenscript/javabytecode/JavaCompiler.java Näytä tiedosto

@@ -5,9 +5,7 @@
5 5
  */
6 6
 package org.openzen.zenscript.javabytecode;
7 7
 
8
-import java.util.ArrayList;
9 8
 import java.util.HashMap;
10
-import java.util.List;
11 9
 import java.util.Map;
12 10
 
13 11
 import org.objectweb.asm.ClassWriter;
@@ -106,7 +104,7 @@ public class JavaCompiler {
106 104
 		implement(INT_TO_FLOAT, JavaWriter::i2f);
107 105
 		implement(INT_TO_DOUBLE, JavaWriter::i2d);
108 106
 		implement(INT_TO_CHAR, JavaWriter::i2s);
109
-		INT_TO_STRING.setTag(JavaMethodInfo.class, new JavaMethodInfo(jInteger, "toString", "(I)Ljava/lang/String;", true));
107
+		INT_TO_STRING.setTag(JavaMethodInfo.class, new JavaMethodInfo(jInteger, "toString", "(I)Ljava/lang/String;", Opcodes.ACC_PUBLIC | Opcodes.ACC_STATIC));
110 108
 		
111 109
 		implement(LONG_TO_BYTE, writer -> { writer.l2i(); writer.i2b(); });
112 110
 		implement(LONG_TO_SBYTE, writer -> { writer.l2i(); writer.i2b(); });
@@ -118,12 +116,12 @@ public class JavaCompiler {
118 116
 		implement(LONG_TO_FLOAT, JavaWriter::l2f);
119 117
 		implement(LONG_TO_DOUBLE, JavaWriter::l2d);
120 118
 		implement(LONG_TO_CHAR, writer -> { writer.l2i(); writer.i2s(); });
121
-		LONG_TO_STRING.setTag(JavaMethodInfo.class, new JavaMethodInfo(jLong, "toString", "(J)Ljava/lang/String;", true));
119
+		LONG_TO_STRING.setTag(JavaMethodInfo.class, new JavaMethodInfo(jLong, "toString", "(J)Ljava/lang/String;", Opcodes.ACC_PUBLIC | Opcodes.ACC_STATIC));
122 120
 		
123
-		FLOAT_BITS.setTag(JavaMethodInfo.class, new JavaMethodInfo(jFloat, "floatToRawIntBits", "(F)I", true));
124
-		DOUBLE_BITS.setTag(JavaMethodInfo.class, new JavaMethodInfo(jDouble, "doubleToRawLongBits", "(D)J", true));
125
-		FLOAT_FROMBITS.setTag(JavaMethodInfo.class, new JavaMethodInfo(jFloat, "intBitsToFloat", "(I)F", true));
126
-		DOUBLE_FROMBITS.setTag(JavaMethodInfo.class, new JavaMethodInfo(jDouble, "longBitsToDouble", "(J)D", true));
121
+		FLOAT_BITS.setTag(JavaMethodInfo.class, new JavaMethodInfo(jFloat, "floatToRawIntBits", "(F)I", Opcodes.ACC_PUBLIC | Opcodes.ACC_STATIC));
122
+		DOUBLE_BITS.setTag(JavaMethodInfo.class, new JavaMethodInfo(jDouble, "doubleToRawLongBits", "(D)J", Opcodes.ACC_PUBLIC | Opcodes.ACC_STATIC));
123
+		FLOAT_FROMBITS.setTag(JavaMethodInfo.class, new JavaMethodInfo(jFloat, "intBitsToFloat", "(I)F", Opcodes.ACC_PUBLIC | Opcodes.ACC_STATIC));
124
+		DOUBLE_FROMBITS.setTag(JavaMethodInfo.class, new JavaMethodInfo(jDouble, "longBitsToDouble", "(J)D", Opcodes.ACC_PUBLIC | Opcodes.ACC_STATIC));
127 125
 	}
128 126
 	
129 127
 	private static void implement(DefinitionMember member, JavaBytecodeImplementation implementation) {
@@ -184,7 +182,8 @@ public class JavaCompiler {
184 182
 		// (TODO: can we break very long scripts into smaller methods? for the extreme scripts)
185 183
 		final JavaClassWriter visitor = scriptBlocks.get(methodName);
186 184
 		visitor.hasRun = true;
187
-		final JavaStatementVisitor statementVisitor = new JavaStatementVisitor(new JavaWriter(visitor, Opcodes.ACC_PUBLIC | Opcodes.ACC_STATIC, "run", "()V", null, null));
185
+		JavaMethodInfo method = new JavaMethodInfo(new JavaClassInfo(methodName), "run", "()V", Opcodes.ACC_PUBLIC | Opcodes.ACC_STATIC);
186
+		final JavaStatementVisitor statementVisitor = new JavaStatementVisitor(new JavaWriter(visitor, method, null, null));
188 187
 		statementVisitor.start();
189 188
 		for (Statement statement : script.statements) {
190 189
 			statement.accept(statementVisitor);
@@ -198,7 +197,8 @@ public class JavaCompiler {
198 197
 			throw new IllegalStateException("Already finished!");
199 198
 		finished = true;
200 199
 		
201
-		final JavaWriter runWriter = new JavaWriter(scriptsClassWriter, Opcodes.ACC_PUBLIC | Opcodes.ACC_STATIC, "run", "()V", null, null);
200
+		JavaMethodInfo runMethod = new JavaMethodInfo(new JavaClassInfo("Scripts"), "run", "()V", Opcodes.ACC_PUBLIC | Opcodes.ACC_STATIC);
201
+		final JavaWriter runWriter = new JavaWriter(scriptsClassWriter, runMethod, null, null);
202 202
 		runWriter.start();
203 203
 		for (Map.Entry<String, JavaClassWriter> entry : scriptBlocks.entrySet()) {
204 204
 			final String owner = entry.getKey();

+ 11
- 9
JavaBytecodeCompiler/src/main/java/org/openzen/zenscript/javabytecode/JavaMethodInfo.java Näytä tiedosto

@@ -5,6 +5,8 @@
5 5
  */
6 6
 package org.openzen.zenscript.javabytecode;
7 7
 
8
+import org.objectweb.asm.Opcodes;
9
+
8 10
 /**
9 11
  *
10 12
  * @author Hoofdgebruiker
@@ -12,17 +14,17 @@ package org.openzen.zenscript.javabytecode;
12 14
 public class JavaMethodInfo {
13 15
 	public final JavaClassInfo javaClass;
14 16
 	public final String name;
15
-	public final String signature;
16
-	public final boolean isStatic;
17
-	
18
-	public JavaMethodInfo(JavaClassInfo javaClass, String name, String signature) {
19
-		this(javaClass, name, signature, false);
20
-	}
17
+	public final String descriptor;
18
+	public final int modifiers;
21 19
 	
22
-	public JavaMethodInfo(JavaClassInfo javaClass, String name, String signature, boolean isStatic) {
20
+	public JavaMethodInfo(JavaClassInfo javaClass, String name, String signature, int modifiers) {
23 21
 		this.javaClass = javaClass;
24 22
 		this.name = name;
25
-		this.signature = signature;
26
-		this.isStatic = isStatic;
23
+		this.descriptor = signature;
24
+		this.modifiers = modifiers;
25
+	}
26
+	
27
+	public boolean isStatic() {
28
+		return (modifiers & Opcodes.ACC_STATIC) > 0;
27 29
 	}
28 30
 }

+ 9
- 24
JavaBytecodeCompiler/src/main/java/org/openzen/zenscript/javabytecode/compiler/JavaExpressionVisitor.java Näytä tiedosto

@@ -16,16 +16,9 @@ import java.util.Map;
16 16
 
17 17
 public class JavaExpressionVisitor implements ExpressionVisitor<Void> {
18 18
     private final JavaWriter javaWriter;
19
-    private final boolean isInit;
20
-
21
-
22
-    public JavaExpressionVisitor(final JavaWriter javaWriter) {
23
-        this(javaWriter, false);
24
-    }
25
-
26
-    public JavaExpressionVisitor(JavaWriter javaWriter, boolean isInit) {
19
+	
20
+    public JavaExpressionVisitor(JavaWriter javaWriter) {
27 21
         this.javaWriter = javaWriter;
28
-        this.isInit = isInit;
29 22
     }
30 23
 
31 24
     private static Class<?> getForEquals(ITypeID id) {
@@ -104,7 +97,7 @@ public class JavaExpressionVisitor implements ExpressionVisitor<Void> {
104 97
         }
105 98
         //TODO: Test with actual static method
106 99
         final JavaMethodInfo info = expression.member.getTag(JavaMethodInfo.class);
107
-        javaWriter.invokeStatic(info.javaClass.internalClassName, info.name, info.signature);
100
+        javaWriter.invokeStatic(info.javaClass.internalClassName, info.name, info.descriptor);
108 101
         return null;
109 102
     }
110 103
 
@@ -459,8 +452,6 @@ public class JavaExpressionVisitor implements ExpressionVisitor<Void> {
459 452
     @Override
460 453
     public Void visitSetField(SetFieldExpression expression) {
461 454
         javaWriter.loadObject(0);
462
-        if (expression.field.isFinal() && !isInit)
463
-            throw new CompileException(expression.position, CompileExceptionCode.CANNOT_SET_FINAL_VARIABLE, "Cannot set a final field!");
464 455
         expression.value.accept(this);
465 456
         if (!checkAndPutFieldInfo(expression.field, false))
466 457
             throw new IllegalStateException("Missing field info on a field member!");
@@ -469,17 +460,13 @@ public class JavaExpressionVisitor implements ExpressionVisitor<Void> {
469 460
 
470 461
     @Override
471 462
     public Void visitSetFunctionParameter(SetFunctionParameterExpression expression) {
472
-        //TODO is static?
473
-        final boolean isStatic = false;
474 463
         expression.value.accept(this);
475
-        javaWriter.store(expression.type.accept(JavaTypeVisitor.INSTANCE), isStatic ? expression.parameter.index : expression.parameter.index + 1);
464
+        javaWriter.store(expression.type.accept(JavaTypeVisitor.INSTANCE), javaWriter.method.isStatic() ? expression.parameter.index : expression.parameter.index + 1);
476 465
         return null;
477 466
     }
478 467
 
479 468
     @Override
480 469
     public Void visitSetLocalVariable(SetLocalVariableExpression expression) {
481
-        if (expression.variable.isFinal)
482
-            throw new CompileException(expression.position, CompileExceptionCode.CANNOT_SET_FINAL_VARIABLE, "Cannot set a final variable!");
483 470
         expression.value.accept(this);
484 471
         Label label = new Label();
485 472
         javaWriter.label(label);
@@ -549,16 +536,14 @@ public class JavaExpressionVisitor implements ExpressionVisitor<Void> {
549 536
         JavaMethodInfo methodInfo = member.getTag(JavaMethodInfo.class);
550 537
         if (methodInfo == null)
551 538
             return false;
552
-        if (methodInfo.isStatic) {
553
-            getJavaWriter().invokeStatic(
554
-                    methodInfo.javaClass.internalClassName,
539
+        if (methodInfo.isStatic()) {
540
+            getJavaWriter().invokeStatic(methodInfo.javaClass.internalClassName,
555 541
                     methodInfo.name,
556
-                    methodInfo.signature);
542
+                    methodInfo.descriptor);
557 543
         } else {
558
-            getJavaWriter().invokeVirtual(
559
-                    methodInfo.javaClass.internalClassName,
544
+            getJavaWriter().invokeVirtual(methodInfo.javaClass.internalClassName,
560 545
                     methodInfo.name,
561
-                    methodInfo.signature);
546
+                    methodInfo.descriptor);
562 547
         }
563 548
         return true;
564 549
     }

+ 3
- 10
JavaBytecodeCompiler/src/main/java/org/openzen/zenscript/javabytecode/compiler/JavaStatementVisitor.java Näytä tiedosto

@@ -8,20 +8,13 @@ import org.openzen.zenscript.javabytecode.JavaLocalVariableInfo;
8 8
 public class JavaStatementVisitor implements StatementVisitor<Void> {
9 9
     private final JavaWriter javaWriter;
10 10
     public final JavaExpressionVisitor expressionVisitor;
11
-    private final boolean isInit;
12
-
13
-    public JavaStatementVisitor(final JavaWriter javaWriter) {
14
-        this(javaWriter, false);
15
-    }
16
-
11
+	
17 12
     /**
18 13
      * @param javaWriter the method writer that compiles the statement
19
-     * @param isInit is the method a class initializer
20 14
      */
21
-    public JavaStatementVisitor(JavaWriter javaWriter, boolean isInit) {
15
+    public JavaStatementVisitor(JavaWriter javaWriter) {
22 16
         this.javaWriter = javaWriter;
23
-        this.expressionVisitor = new JavaExpressionVisitor(javaWriter, isInit);
24
-        this.isInit = isInit;
17
+        this.expressionVisitor = new JavaExpressionVisitor(javaWriter);
25 18
     }
26 19
 
27 20
     @Override

+ 10
- 5
JavaBytecodeCompiler/src/main/java/org/openzen/zenscript/javabytecode/compiler/JavaWriter.java Näytä tiedosto

@@ -12,8 +12,11 @@ import java.util.List;
12 12
 import java.util.Map;
13 13
 
14 14
 import static org.objectweb.asm.Opcodes.*;
15
+import org.openzen.zenscript.javabytecode.JavaMethodInfo;
15 16
 
16 17
 public class JavaWriter {
18
+	public final JavaMethodInfo method;
19
+	
17 20
     private final LocalVariablesSorter visitor;
18 21
     private final List<JavaLocalVariableInfo> localVariableInfos = new ArrayList<>();
19 22
     private boolean debug = false;
@@ -21,19 +24,21 @@ public class JavaWriter {
21 24
     private int labelIndex = 1;
22 25
     private Map<Label, String> labelNames = new HashMap<>();
23 26
 
24
-    public JavaWriter(ClassVisitor visitor, boolean nameVariables, int access, String name, String description, String signature, String[] exceptions, String... annotations) {
25
-        final MethodVisitor methodVisitor = visitor.visitMethod(access, name, description, signature, exceptions);
27
+    public JavaWriter(ClassVisitor visitor, boolean nameVariables, JavaMethodInfo method, String signature, String[] exceptions, String... annotations) {
28
+		this.method = method;
29
+		
30
+        final MethodVisitor methodVisitor = visitor.visitMethod(method.modifiers, method.name, method.descriptor, signature, exceptions);
26 31
 
27 32
         for (String annotation : annotations) {
28 33
             methodVisitor.visitAnnotation(annotation, true).visitEnd();
29 34
         }
30 35
 
31
-        this.visitor = new LocalVariablesSorter(access, description, methodVisitor);
36
+        this.visitor = new LocalVariablesSorter(method.modifiers, method.descriptor, methodVisitor);
32 37
         this.nameVariables = nameVariables;
33 38
     }
34 39
 
35
-    public JavaWriter(ClassVisitor visitor, int access, String name, String description, String signature, String[] exceptions, String... annotations) {
36
-        this(visitor, true, access, name, description, signature, exceptions, annotations);
40
+    public JavaWriter(ClassVisitor visitor, JavaMethodInfo method, String signature, String[] exceptions, String... annotations) {
41
+        this(visitor, true, method, signature, exceptions, annotations);
37 42
     }
38 43
 
39 44
     private static String signature(Class aClass) {

+ 20
- 19
JavaBytecodeCompiler/src/main/java/org/openzen/zenscript/javabytecode/compiler/definitions/JavaDefinitionVisitor.java Näytä tiedosto

@@ -7,7 +7,6 @@ import org.openzen.zenscript.codemodel.FunctionParameter;
7 7
 import org.openzen.zenscript.codemodel.definition.*;
8 8
 import org.openzen.zenscript.codemodel.expression.Expression;
9 9
 import org.openzen.zenscript.codemodel.expression.ExpressionVisitor;
10
-import org.openzen.zenscript.codemodel.generic.TypeParameter;
11 10
 import org.openzen.zenscript.codemodel.member.ConstructorMember;
12 11
 import org.openzen.zenscript.codemodel.member.EnumConstantMember;
13 12
 import org.openzen.zenscript.codemodel.member.FieldMember;
@@ -20,7 +19,6 @@ import org.openzen.zenscript.codemodel.type.ITypeID;
20 19
 import org.openzen.zenscript.javabytecode.JavaClassInfo;
21 20
 import org.openzen.zenscript.javabytecode.JavaEnumInfo;
22 21
 import org.openzen.zenscript.javabytecode.JavaMethodInfo;
23
-import org.openzen.zenscript.javabytecode.TestIsStaticInfo;
24 22
 import org.openzen.zenscript.javabytecode.compiler.*;
25 23
 
26 24
 import java.util.Iterator;
@@ -45,6 +43,7 @@ public class JavaDefinitionVisitor implements DefinitionVisitor<byte[]> {
45 43
         else
46 44
             superType = Type.getType(definition.superType.accept(JavaTypeClassVisitor.INSTANCE));
47 45
 
46
+		JavaClassInfo toClass = new JavaClassInfo(definition.name);
48 47
         JavaClassWriter writer = new JavaClassWriter(ClassWriter.COMPUTE_FRAMES);
49 48
 
50 49
         //TODO: Calculate signature from generic parameters
@@ -56,8 +55,6 @@ public class JavaDefinitionVisitor implements DefinitionVisitor<byte[]> {
56 55
         for (IDefinitionMember member : definition.members) {
57 56
             if (member instanceof ConstructorMember) {
58 57
                 final ConstructorMember constructorMember = (ConstructorMember) member;
59
-
60
-
61 58
                 constructorMember.body.add(0, new ExpressionStatement(constructorMember.position, new Expression(constructorMember.position, BasicTypeID.VOID) {
62 59
                     @Override
63 60
                     public <T> T accept(ExpressionVisitor<T> visitor) {
@@ -79,9 +76,8 @@ public class JavaDefinitionVisitor implements DefinitionVisitor<byte[]> {
79 76
                     }
80 77
                 }));
81 78
             }
82
-            member.accept(new JavaMemberVisitor(writer, definition.name));
83
-
84
-
79
+			
80
+            member.accept(new JavaMemberVisitor(writer, toClass));
85 81
         }
86 82
         writer.visitEnd();
87 83
         return writer.toByteArray();
@@ -89,6 +85,7 @@ public class JavaDefinitionVisitor implements DefinitionVisitor<byte[]> {
89 85
 
90 86
     @Override
91 87
     public byte[] visitInterface(InterfaceDefinition definition) {
88
+		JavaClassInfo toClass = new JavaClassInfo(definition.name);
92 89
         ClassWriter writer = new ClassWriter(ClassWriter.COMPUTE_FRAMES);
93 90
 
94 91
         //TODO: Calculate signature from generic parameters
@@ -96,7 +93,7 @@ public class JavaDefinitionVisitor implements DefinitionVisitor<byte[]> {
96 93
         String signature = null;
97 94
         writer.visit(Opcodes.V1_8, definition.modifiers | Opcodes.ACC_INTERFACE | Opcodes.ACC_ABSTRACT, definition.name, signature, Type.getInternalName(Object.class), null);
98 95
         for (IDefinitionMember member : definition.members) {
99
-            member.accept(new JavaMemberVisitor(writer, definition.name));
96
+            member.accept(new JavaMemberVisitor(writer, toClass));
100 97
         }
101 98
         writer.visitEnd();
102 99
         return writer.toByteArray();
@@ -123,8 +120,10 @@ public class JavaDefinitionVisitor implements DefinitionVisitor<byte[]> {
123 120
             }
124 121
         }
125 122
 
126
-        final JavaWriter clinitWriter = new JavaWriter(writer, true, Opcodes.ACC_STATIC, "<clinit>", "()V", null, null);
127
-        final JavaStatementVisitor clinitVisitor = new JavaStatementVisitor(clinitWriter, true);
123
+		JavaClassInfo toClass = new JavaClassInfo(definition.name);
124
+		JavaMethodInfo clinitInfo = new JavaMethodInfo(toClass, "<clinit>", "()V", Opcodes.ACC_STATIC);
125
+        final JavaWriter clinitWriter = new JavaWriter(writer, clinitInfo, null, null);
126
+        final JavaStatementVisitor clinitVisitor = new JavaStatementVisitor(clinitWriter);
128 127
         clinitVisitor.start();
129 128
         int constantCount = 0;
130 129
         for (IDefinitionMember member : definition.members) {
@@ -151,7 +150,7 @@ public class JavaDefinitionVisitor implements DefinitionVisitor<byte[]> {
151 150
                 ++constantCount;
152 151
                 member.setTag(JavaEnumInfo.class, new JavaEnumInfo(clinitVisitor));
153 152
             }
154
-            member.accept(new JavaMemberVisitor(writer, definition.name));
153
+            member.accept(new JavaMemberVisitor(writer, toClass));
155 154
         }
156 155
 
157 156
         clinitWriter.constant(constantCount);
@@ -171,7 +170,8 @@ public class JavaDefinitionVisitor implements DefinitionVisitor<byte[]> {
171 170
         //Enum Stuff(required!)
172 171
         writer.visitField(Opcodes.ACC_STATIC | Opcodes.ACC_PRIVATE | Opcodes.ACC_FINAL | Opcodes.ACC_SYNTHETIC, "$VALUES", "[L" + definition.name + ";", null, null).visitEnd();
173 172
 
174
-        JavaWriter valuesWriter = new JavaWriter(writer, true, Opcodes.ACC_STATIC | Opcodes.ACC_PUBLIC, "values", "()[L" + definition.name + ";", null, null);
173
+		JavaMethodInfo valuesMethodInfo = new JavaMethodInfo(toClass, "values", "()[L" + definition.name + ";", Opcodes.ACC_STATIC | Opcodes.ACC_PUBLIC);
174
+        JavaWriter valuesWriter = new JavaWriter(writer, true, valuesMethodInfo, null, null);
175 175
         valuesWriter.start();
176 176
         valuesWriter.getStaticField(definition.name, "$VALUES", "[L" + definition.name + ";");
177 177
         valuesWriter.invokeVirtual("[L" + definition.name + ";", "clone", "()Ljava/lang/Object;");
@@ -179,8 +179,8 @@ public class JavaDefinitionVisitor implements DefinitionVisitor<byte[]> {
179 179
         valuesWriter.returnObject();
180 180
         valuesWriter.end();
181 181
 
182
-
183
-        JavaWriter valueOfWriter = new JavaWriter(writer, true, Opcodes.ACC_STATIC | Opcodes.ACC_PUBLIC, "valueOf", "(Ljava/lang/String;)L" + definition.name + ";", null, null);
182
+		JavaMethodInfo valueOfMethodInfo = new JavaMethodInfo(toClass, "valueOf", "(Ljava/lang/String;)L" + definition.name + ";", Opcodes.ACC_STATIC | Opcodes.ACC_PUBLIC);
183
+        JavaWriter valueOfWriter = new JavaWriter(writer, true, valueOfMethodInfo, null, null);
184 184
         valueOfWriter.start();
185 185
         valueOfWriter.invokeStatic("java/lang/Class", "forName", "(Ljava/lang/String;)Ljava/lang/Class;");
186 186
         valueOfWriter.loadObject(0);
@@ -202,7 +202,11 @@ public class JavaDefinitionVisitor implements DefinitionVisitor<byte[]> {
202 202
     @Override
203 203
     public byte[] visitFunction(FunctionDefinition definition) {
204 204
         final String signature = CompilerUtils.calcSign(definition.header, false);
205
-        final JavaWriter writer = new JavaWriter(outerWriter, true, CompilerUtils.calcAccess(definition.modifiers) | Opcodes.ACC_STATIC, definition.name, CompilerUtils.calcDesc(definition.header, false), signature, null);
205
+		
206
+		final JavaClassInfo toClass = new JavaClassInfo(CompilerUtils.calcClasName(definition.position));
207
+		final JavaMethodInfo methodInfo = new JavaMethodInfo(toClass, definition.name, CompilerUtils.calcDesc(definition.header, false), CompilerUtils.calcAccess(definition.modifiers) | Opcodes.ACC_STATIC);
208
+
209
+		final JavaWriter writer = new JavaWriter(outerWriter, true, methodInfo, signature, null);
206 210
         final JavaStatementVisitor statementVisitor = new JavaStatementVisitor(writer);
207 211
         statementVisitor.start();
208 212
         final Iterator<Statement> statementIterator = definition.statements.iterator();
@@ -222,13 +226,10 @@ public class JavaDefinitionVisitor implements DefinitionVisitor<byte[]> {
222 226
                     writer.aConstNull();
223 227
                 writer.returnType(type.accept(JavaTypeVisitor.INSTANCE));
224 228
             }
225
-
226 229
         }
227 230
 
228 231
         statementVisitor.end();
229
-
230
-        final JavaMethodInfo methodInfo = new JavaMethodInfo(new JavaClassInfo(CompilerUtils.calcClasName(definition.position)), definition.name, signature, true);
231
-
232
+		
232 233
         definition.setTag(JavaMethodInfo.class, methodInfo);
233 234
         definition.caller.setTag(JavaMethodInfo.class, methodInfo);
234 235
         return null;

+ 22
- 13
JavaBytecodeCompiler/src/main/java/org/openzen/zenscript/javabytecode/compiler/definitions/JavaMemberVisitor.java Näytä tiedosto

@@ -6,10 +6,8 @@ import org.objectweb.asm.Opcodes;
6 6
 import org.objectweb.asm.Type;
7 7
 import org.openzen.zenscript.codemodel.FunctionParameter;
8 8
 import org.openzen.zenscript.codemodel.Modifiers;
9
-import org.openzen.zenscript.codemodel.expression.ConstructorThisCallExpression;
10 9
 import org.openzen.zenscript.codemodel.expression.Expression;
11 10
 import org.openzen.zenscript.codemodel.member.*;
12
-import org.openzen.zenscript.codemodel.statement.ExpressionStatement;
13 11
 import org.openzen.zenscript.codemodel.statement.Statement;
14 12
 import org.openzen.zenscript.javabytecode.JavaClassInfo;
15 13
 import org.openzen.zenscript.javabytecode.JavaEnumInfo;
@@ -20,11 +18,11 @@ import org.openzen.zenscript.javabytecode.compiler.*;
20 18
 public class JavaMemberVisitor implements MemberVisitor<Void> {
21 19
 
22 20
     private final ClassWriter writer;
23
-    private final String className;
21
+	private final JavaClassInfo toClass;
24 22
 
25
-    public JavaMemberVisitor(ClassWriter writer, String className) {
23
+    public JavaMemberVisitor(ClassWriter writer, JavaClassInfo toClass) {
26 24
         this.writer = writer;
27
-        this.className = className;
25
+		this.toClass = toClass;
28 26
     }
29 27
 
30 28
     @Override
@@ -34,23 +32,26 @@ public class JavaMemberVisitor implements MemberVisitor<Void> {
34 32
         String signature = null;
35 33
         final String descriptor = Type.getDescriptor(member.type.accept(JavaTypeClassVisitor.INSTANCE));
36 34
         writer.visitField(member.modifiers, member.name, descriptor, signature, null).visitEnd();
37
-        member.setTag(JavaFieldInfo.class, new JavaFieldInfo(new JavaClassInfo(className), member.name, descriptor));
35
+        member.setTag(JavaFieldInfo.class, new JavaFieldInfo(toClass, member.name, descriptor));
38 36
         return null;
39 37
     }
40 38
 
41 39
     @Override
42 40
     public Void visitConstructor(ConstructorMember member) {
41
+        final boolean isEnum = member.hasTag(JavaEnumInfo.class);
42
+		String descriptor = CompilerUtils.calcDesc(member.header, isEnum);
43
+		final JavaMethodInfo method = new JavaMethodInfo(toClass, "<init>", descriptor, isEnum ? Opcodes.ACC_PRIVATE : CompilerUtils.calcAccess(member.modifiers));
44
+		
43 45
         final Label constructorStart = new Label();
44 46
         final Label constructorEnd = new Label();
45
-        final boolean isEnum = member.hasTag(JavaEnumInfo.class);
46
-        final JavaWriter constructorWriter = new JavaWriter(writer, isEnum ? Opcodes.ACC_PRIVATE : member.modifiers, "<init>", CompilerUtils.calcDesc(member.header, isEnum), CompilerUtils.calcSign(member.header, isEnum), null);
47
+        final JavaWriter constructorWriter = new JavaWriter(writer, method, CompilerUtils.calcSign(member.header, isEnum), null);
47 48
         constructorWriter.label(constructorStart);
48 49
         for (FunctionParameter parameter : member.header.parameters) {
49 50
             if(isEnum)
50 51
                 parameter.index += 2;
51 52
             constructorWriter.nameVariable(parameter.index + 1, parameter.name, constructorStart, constructorEnd, Type.getType(parameter.type.accept(JavaTypeClassVisitor.INSTANCE)));
52 53
         }
53
-        final JavaStatementVisitor statementVisitor = new JavaStatementVisitor(constructorWriter, true);
54
+        final JavaStatementVisitor statementVisitor = new JavaStatementVisitor(constructorWriter);
54 55
         statementVisitor.start();
55 56
 
56 57
         for (Statement statement : member.body) {
@@ -63,10 +64,19 @@ public class JavaMemberVisitor implements MemberVisitor<Void> {
63 64
 
64 65
     @Override
65 66
     public Void visitMethod(MethodMember member) {
67
+        final boolean isAbstract = member.body == null || member.body.isEmpty() || Modifiers.isAbstract(member.modifiers);
68
+		int modifiers = (isAbstract ? Opcodes.ACC_ABSTRACT : 0)
69
+				| (member.isStatic() ? Opcodes.ACC_STATIC : 0)
70
+				| CompilerUtils.calcAccess(member.modifiers);
71
+		final JavaMethodInfo method = new JavaMethodInfo(
72
+				toClass,
73
+				member.name,
74
+				CompilerUtils.calcSign(member.header, false),
75
+				modifiers);
76
+		
66 77
         final Label methodStart = new Label();
67 78
         final Label methodEnd = new Label();
68
-        final boolean isAbstract = member.body == null || member.body.isEmpty() || Modifiers.isAbstract(member.modifiers);
69
-        final JavaWriter methodWriter = new JavaWriter(writer, isAbstract ? member.modifiers | Opcodes.ACC_ABSTRACT : member.modifiers, member.name, CompilerUtils.calcDesc(member.header, false), CompilerUtils.calcSign(member.header, false), null);
79
+        final JavaWriter methodWriter = new JavaWriter(writer, method, CompilerUtils.calcSign(member.header, false), null);
70 80
         methodWriter.label(methodStart);
71 81
         for (final FunctionParameter parameter : member.header.parameters) {
72 82
             methodWriter.nameParameter(0, parameter.name);
@@ -86,8 +96,7 @@ public class JavaMemberVisitor implements MemberVisitor<Void> {
86 96
             statementVisitor.end();
87 97
         }
88 98
 
89
-        member.setTag(JavaMethodInfo.class, new JavaMethodInfo(new JavaClassInfo(className), member.name, CompilerUtils.calcSign(member.header, false), member.isStatic()));
90
-
99
+        member.setTag(JavaMethodInfo.class, method);
91 100
         return null;
92 101
     }
93 102
 

+ 3
- 2
ScriptingExample/src/main/java/org/openzen/zenscript/scriptingexample/GlobalRegistry.java Näytä tiedosto

@@ -10,6 +10,7 @@ import java.util.ArrayList;
10 10
 import java.util.HashMap;
11 11
 import java.util.List;
12 12
 import java.util.Map;
13
+import org.objectweb.asm.Opcodes;
13 14
 import org.openzen.zenscript.codemodel.FunctionHeader;
14 15
 import org.openzen.zenscript.codemodel.FunctionParameter;
15 16
 import org.openzen.zenscript.codemodel.Modifiers;
@@ -46,7 +47,7 @@ public class GlobalRegistry {
46 47
 	
47 48
 	public GlobalRegistry(ZSPackage globals) {
48 49
 		JavaClassInfo jPrintStream = new JavaClassInfo("java/io/PrintStream");
49
-		PRINTSTREAM_PRINTLN.setTag(JavaMethodInfo.class, new JavaMethodInfo(jPrintStream, "println", "(Ljava/lang/String;)V"));
50
+		PRINTSTREAM_PRINTLN.setTag(JavaMethodInfo.class, new JavaMethodInfo(jPrintStream, "println", "(Ljava/lang/String;)V", Opcodes.ACC_PUBLIC));
50 51
 		
51 52
 		JavaClassInfo jSystem = new JavaClassInfo("java/lang/System");
52 53
 		SYSTEM_OUT.setTag(JavaFieldInfo.class, new JavaFieldInfo(jSystem, "out", "Ljava/io/PrintStream;"));
@@ -68,7 +69,7 @@ public class GlobalRegistry {
68 69
 			JavaClassInfo myClassInfo = new JavaClassInfo("my/test/MyClass");
69 70
 			
70 71
 			MethodMember member = new MethodMember(CodePosition.NATIVE, myClassDefinition, Modifiers.PUBLIC, "test", new FunctionHeader(BasicTypeID.STRING));
71
-			member.setTag(JavaMethodInfo.class, new JavaMethodInfo(myClassInfo, "test", "()Ljava/lang/String;"));
72
+			member.setTag(JavaMethodInfo.class, new JavaMethodInfo(myClassInfo, "test", "()Ljava/lang/String;", Opcodes.ACC_PUBLIC));
72 73
 			myClassDefinition.addMember(member);
73 74
 			
74 75
 			packageMyPackage.register(myClassDefinition);

Loading…
Peruuta
Tallenna