Mercurial > hg > graal-compiler
comparison graal/com.oracle.truffle.dsl.processor/src/com/oracle/truffle/dsl/processor/typesystem/TypeSystemCodeGenerator.java @ 11545:2fb276f5e3e9
Truffle-DSL: implemented implicit casts.
author | Christian Humer <christian.humer@gmail.com> |
---|---|
date | Fri, 06 Sep 2013 16:16:40 +0200 |
parents | b7f90ff38d4b |
children | 8e8347ecabbc |
comparison
equal
deleted
inserted
replaced
11544:e5b5a5cb0ac7 | 11545:2fb276f5e3e9 |
---|---|
42 | 42 |
43 public static String isTypeMethodName(TypeData type) { | 43 public static String isTypeMethodName(TypeData type) { |
44 return "is" + Utils.getTypeId(type.getBoxedType()); | 44 return "is" + Utils.getTypeId(type.getBoxedType()); |
45 } | 45 } |
46 | 46 |
47 public static String isImplicitTypeMethodName(TypeData type) { | |
48 return "isImplicit" + Utils.getTypeId(type.getBoxedType()); | |
49 } | |
50 | |
47 public static String asTypeMethodName(TypeData type) { | 51 public static String asTypeMethodName(TypeData type) { |
48 return "as" + Utils.getTypeId(type.getBoxedType()); | 52 return "as" + Utils.getTypeId(type.getBoxedType()); |
53 } | |
54 | |
55 public static String asImplicitTypeMethodName(TypeData type) { | |
56 return "asImplicit" + Utils.getTypeId(type.getBoxedType()); | |
57 } | |
58 | |
59 public static String getImplicitClass(TypeData type) { | |
60 return "getImplicit" + Utils.getTypeId(type.getBoxedType()) + "Class"; | |
49 } | 61 } |
50 | 62 |
51 public static String expectTypeMethodName(TypeData type) { | 63 public static String expectTypeMethodName(TypeData type) { |
52 return "expect" + Utils.getTypeId(type.getBoxedType()); | 64 return "expect" + Utils.getTypeId(type.getBoxedType()); |
53 } | 65 } |
98 CodeExecutableElement expect = createExpectTypeMethod(type, sourceType); | 110 CodeExecutableElement expect = createExpectTypeMethod(type, sourceType); |
99 if (expect != null) { | 111 if (expect != null) { |
100 clazz.add(expect); | 112 clazz.add(expect); |
101 } | 113 } |
102 } | 114 } |
115 | |
116 CodeExecutableElement asImplicit = createAsImplicitTypeMethod(type); | |
117 if (asImplicit != null) { | |
118 clazz.add(asImplicit); | |
119 } | |
120 CodeExecutableElement isImplicit = createIsImplicitTypeMethod(type); | |
121 if (isImplicit != null) { | |
122 clazz.add(isImplicit); | |
123 } | |
124 | |
125 CodeExecutableElement typeIndex = createGetTypeIndex(type); | |
126 if (typeIndex != null) { | |
127 clazz.add(typeIndex); | |
128 } | |
103 } | 129 } |
104 } | 130 } |
105 | 131 |
106 return clazz; | 132 return clazz; |
107 } | 133 } |
131 CodeVariableElement field = new CodeVariableElement(modifiers(PUBLIC, STATIC, FINAL), clazz.asType(), singletonName(getModel().getTemplateType().asType())); | 157 CodeVariableElement field = new CodeVariableElement(modifiers(PUBLIC, STATIC, FINAL), clazz.asType(), singletonName(getModel().getTemplateType().asType())); |
132 field.createInitBuilder().startNew(clazz.asType()).end(); | 158 field.createInitBuilder().startNew(clazz.asType()).end(); |
133 return field; | 159 return field; |
134 } | 160 } |
135 | 161 |
162 private CodeExecutableElement createIsImplicitTypeMethod(TypeData type) { | |
163 TypeSystemData typeSystem = getModel(); | |
164 List<ImplicitCastData> casts = typeSystem.lookupByTargetType(type); | |
165 if (casts.isEmpty()) { | |
166 return null; | |
167 } | |
168 CodeExecutableElement method = new CodeExecutableElement(modifiers(PUBLIC), getContext().getType(boolean.class), TypeSystemCodeGenerator.isImplicitTypeMethodName(type)); | |
169 method.addParameter(new CodeVariableElement(getContext().getType(Object.class), LOCAL_VALUE)); | |
170 CodeTreeBuilder builder = method.createBuilder(); | |
171 | |
172 List<TypeData> sourceTypes = typeSystem.lookupSourceTypes(type); | |
173 | |
174 builder.startReturn(); | |
175 String sep = ""; | |
176 for (TypeData sourceType : sourceTypes) { | |
177 builder.string(sep); | |
178 builder.startCall(isTypeMethodName(sourceType)).string(LOCAL_VALUE).end(); | |
179 sep = " || "; | |
180 } | |
181 builder.end(); | |
182 return method; | |
183 } | |
184 | |
185 private CodeExecutableElement createAsImplicitTypeMethod(TypeData type) { | |
186 TypeSystemData typeSystem = getModel(); | |
187 List<ImplicitCastData> casts = typeSystem.lookupByTargetType(type); | |
188 if (casts.isEmpty()) { | |
189 return null; | |
190 } | |
191 CodeExecutableElement method = new CodeExecutableElement(modifiers(PUBLIC), type.getPrimitiveType(), TypeSystemCodeGenerator.asImplicitTypeMethodName(type)); | |
192 method.addParameter(new CodeVariableElement(getContext().getType(Object.class), LOCAL_VALUE)); | |
193 | |
194 List<TypeData> sourceTypes = typeSystem.lookupSourceTypes(type); | |
195 | |
196 CodeTreeBuilder builder = method.createBuilder(); | |
197 boolean elseIf = false; | |
198 for (TypeData sourceType : sourceTypes) { | |
199 elseIf = builder.startIf(elseIf); | |
200 builder.startCall(isTypeMethodName(sourceType)).string(LOCAL_VALUE).end(); | |
201 builder.end().startBlock(); | |
202 | |
203 builder.startReturn(); | |
204 ImplicitCastData cast = typeSystem.lookupCast(sourceType, type); | |
205 if (cast != null) { | |
206 builder.startCall(cast.getMethodName()); | |
207 } | |
208 builder.startCall(asTypeMethodName(sourceType)).string(LOCAL_VALUE).end(); | |
209 if (cast != null) { | |
210 builder.end(); | |
211 } | |
212 builder.end(); | |
213 builder.end(); | |
214 } | |
215 | |
216 builder.startElseBlock(); | |
217 builder.startStatement().startStaticCall(getContext().getTruffleTypes().getCompilerDirectives(), "transferToInterpreter").end().end(); | |
218 builder.startThrow().startNew(getContext().getType(IllegalArgumentException.class)).doubleQuote("Illegal type ").end().end(); | |
219 builder.end(); | |
220 return method; | |
221 } | |
222 | |
223 private CodeExecutableElement createGetTypeIndex(TypeData type) { | |
224 TypeSystemData typeSystem = getModel(); | |
225 List<ImplicitCastData> casts = typeSystem.lookupByTargetType(type); | |
226 if (casts.isEmpty()) { | |
227 return null; | |
228 } | |
229 CodeExecutableElement method = new CodeExecutableElement(modifiers(PUBLIC), getContext().getType(Class.class), TypeSystemCodeGenerator.getImplicitClass(type)); | |
230 method.addParameter(new CodeVariableElement(getContext().getType(Object.class), LOCAL_VALUE)); | |
231 | |
232 List<TypeData> sourceTypes = typeSystem.lookupSourceTypes(type); | |
233 CodeTreeBuilder builder = method.createBuilder(); | |
234 boolean elseIf = false; | |
235 for (TypeData sourceType : sourceTypes) { | |
236 elseIf = builder.startIf(elseIf); | |
237 builder.startCall(isTypeMethodName(sourceType)).string(LOCAL_VALUE).end(); | |
238 builder.end().startBlock(); | |
239 builder.startReturn().typeLiteral(sourceType.getPrimitiveType()).end(); | |
240 builder.end(); | |
241 } | |
242 | |
243 builder.startElseBlock(); | |
244 builder.startStatement().startStaticCall(getContext().getTruffleTypes().getCompilerDirectives(), "transferToInterpreter").end().end(); | |
245 builder.startThrow().startNew(getContext().getType(IllegalArgumentException.class)).doubleQuote("Illegal type ").end().end(); | |
246 builder.end(); | |
247 | |
248 return method; | |
249 } | |
250 | |
136 private CodeExecutableElement createIsTypeMethod(TypeData type) { | 251 private CodeExecutableElement createIsTypeMethod(TypeData type) { |
137 if (!type.getTypeChecks().isEmpty()) { | 252 if (!type.getTypeChecks().isEmpty()) { |
138 return null; | 253 return null; |
139 } | 254 } |
140 | 255 |
172 CodeExecutableElement method = new CodeExecutableElement(modifiers(PUBLIC), expectedType.getPrimitiveType(), TypeSystemCodeGenerator.expectTypeMethodName(expectedType)); | 287 CodeExecutableElement method = new CodeExecutableElement(modifiers(PUBLIC), expectedType.getPrimitiveType(), TypeSystemCodeGenerator.expectTypeMethodName(expectedType)); |
173 method.addParameter(new CodeVariableElement(sourceType.getPrimitiveType(), LOCAL_VALUE)); | 288 method.addParameter(new CodeVariableElement(sourceType.getPrimitiveType(), LOCAL_VALUE)); |
174 method.addThrownType(getContext().getTruffleTypes().getUnexpectedValueException()); | 289 method.addThrownType(getContext().getTruffleTypes().getUnexpectedValueException()); |
175 | 290 |
176 CodeTreeBuilder body = method.createBuilder(); | 291 CodeTreeBuilder body = method.createBuilder(); |
177 body.startIf().startCall(null, TypeSystemCodeGenerator.isTypeMethodName(expectedType)).string(LOCAL_VALUE).end().end().startBlock(); | 292 body.startIf().startCall(TypeSystemCodeGenerator.isTypeMethodName(expectedType)).string(LOCAL_VALUE).end().end().startBlock(); |
178 body.startReturn().startCall(null, TypeSystemCodeGenerator.asTypeMethodName(expectedType)).string(LOCAL_VALUE).end().end(); | 293 body.startReturn().startCall(TypeSystemCodeGenerator.asTypeMethodName(expectedType)).string(LOCAL_VALUE).end().end(); |
179 body.end(); // if-block | 294 body.end(); // if-block |
180 body.startThrow().startNew(getContext().getTruffleTypes().getUnexpectedValueException()).string(LOCAL_VALUE).end().end(); | 295 body.startThrow().startNew(getContext().getTruffleTypes().getUnexpectedValueException()).string(LOCAL_VALUE).end().end(); |
181 | 296 |
182 return method; | 297 return method; |
183 } | 298 } |