]> gerrit.simantics Code Review - simantics/platform.git/blob - bundles/org.simantics.scl.compiler/src/org/simantics/scl/compiler/constants/generic/CallJava.java
300f11802ae4df144649a7d0a6f156294dc6e999
[simantics/platform.git] / bundles / org.simantics.scl.compiler / src / org / simantics / scl / compiler / constants / generic / CallJava.java
1 package org.simantics.scl.compiler.constants.generic;\r
2 \r
3 import org.cojen.classfile.TypeDesc;\r
4 import org.simantics.scl.compiler.constants.FunctionValue;\r
5 import org.simantics.scl.compiler.internal.codegen.references.Val;\r
6 import org.simantics.scl.compiler.internal.codegen.types.JavaReferenceValidator;\r
7 import org.simantics.scl.compiler.internal.codegen.utils.MethodBuilder;\r
8 import org.simantics.scl.compiler.types.TVar;\r
9 import org.simantics.scl.compiler.types.Type;\r
10 \r
11 /**\r
12  * This class represents a call to a Java method as an SCL function value.\r
13  * It is instantiated by the {@link org.simantics.scl.compiler.compilation.Elaboration.matchType(MethodRef, Type)} method. \r
14  */\r
15 public class CallJava extends FunctionValue {\r
16     StackItem[] stackItems;\r
17     MethodRef methodRef;\r
18     OutputFilter filter;\r
19     \r
20     public CallJava(TVar[] typeParameters, Type effect, Type returnType,\r
21             Type[] parameterTypes, StackItem[] stackItems, MethodRef methodRef,\r
22             OutputFilter filter) {\r
23         super(typeParameters, effect, returnType, parameterTypes);\r
24         this.stackItems = stackItems;\r
25         this.methodRef = methodRef;\r
26         this.filter = filter;\r
27     }\r
28 \r
29     @Override\r
30     public Type applyExact(MethodBuilder mb, Val[] parameters) {\r
31         methodRef.invoke(mb, stackItems, parameters);\r
32         if(filter != null)\r
33             filter.filter(mb);\r
34         return getReturnType();\r
35     }\r
36     \r
37     public MethodRef getMethodRef() {\r
38         return methodRef;\r
39     }\r
40     \r
41     @Override\r
42     public String toString() {\r
43         return methodRef.getName();\r
44     }\r
45 \r
46     public final static int INCOMPARABLE = -2;\r
47     public final static int LESS = -1;\r
48     public final static int EQUAL = 0;\r
49     public final static int GREATER = 1;\r
50     \r
51     public int compareTo(JavaReferenceValidator validator, CallJava other) {\r
52         MethodRef m1 = methodRef;\r
53         MethodRef m2 = other.methodRef;\r
54         TypeDesc[] ps1 = m1.getParameterTypes();\r
55         TypeDesc[] ps2 = m2.getParameterTypes();\r
56         if(ps1.length != ps2.length)\r
57             return INCOMPARABLE;\r
58 \r
59         boolean lessOrEqual = true;\r
60         boolean greaterOrEqual = true;\r
61         for(int i=0;i<ps1.length;++i) {\r
62             if(ps1[i].equals(ps2[i]))\r
63                 continue;\r
64             if(!validator.isAssignableFrom(ps1[i], ps2[i])) {\r
65                 lessOrEqual = false;\r
66             }\r
67             if(!validator.isAssignableFrom(ps2[i], ps1[i])) {\r
68                 greaterOrEqual = false;\r
69             }\r
70         }\r
71         if(lessOrEqual) {\r
72             if(greaterOrEqual)\r
73                 return EQUAL;\r
74             else\r
75                 return LESS;\r
76         }\r
77         else {\r
78             if(greaterOrEqual)\r
79                 return GREATER;\r
80             else\r
81                 return INCOMPARABLE;\r
82         }\r
83     }\r
84     \r
85     @Override\r
86     public void prepare(MethodBuilder mb) {\r
87         for(StackItem item : stackItems)\r
88             item.prepare(mb);\r
89     }\r
90 }\r