Mercurial > hg > graal-jvmci-8
comparison graal/com.oracle.truffle.codegen.processor/src/com/oracle/truffle/codegen/processor/template/TemplateMethodParser.java @ 8237:6b74ffe38183
Implemented support for executing nodes in @Children fields.
author | Christian Humer <christian.humer@gmail.com> |
---|---|
date | Fri, 01 Mar 2013 17:03:57 +0100 |
parents | c17ee8823d72 |
children | ac4e8c16ffdf |
comparison
equal
deleted
inserted
replaced
7860:dbbdc0a30a16 | 8237:6b74ffe38183 |
---|---|
99 getContext().getLog().error(method, "Method must not be private."); | 99 getContext().getLog().error(method, "Method must not be private."); |
100 valid = false; | 100 valid = false; |
101 continue; | 101 continue; |
102 } | 102 } |
103 | 103 |
104 E parsedMethod = parse(method, mirror); | 104 E parsedMethod = parseNew(method, mirror); |
105 if (parsedMethod != null) { | 105 if (parsedMethod != null) { |
106 parsedMethods.add(parsedMethod); | 106 parsedMethods.add(parsedMethod); |
107 } else { | 107 } else { |
108 valid = false; | 108 valid = false; |
109 } | 109 } |
112 return null; | 112 return null; |
113 } | 113 } |
114 return parsedMethods; | 114 return parsedMethods; |
115 } | 115 } |
116 | 116 |
117 private E parse(ExecutableElement method, AnnotationMirror annotation) { | 117 private E parseNew(ExecutableElement method, AnnotationMirror annotation) { |
118 MethodSpec methodSpecification = createSpecification(method, annotation); | 118 MethodSpec methodSpecification = createSpecification(method, annotation); |
119 if (methodSpecification == null) { | 119 if (methodSpecification == null) { |
120 return null; | 120 return null; |
121 } | 121 } |
122 | 122 |
124 | 124 |
125 ParameterSpec returnTypeSpec = methodSpecification.getReturnType(); | 125 ParameterSpec returnTypeSpec = methodSpecification.getReturnType(); |
126 List<ParameterSpec> parameterSpecs = new ArrayList<>(); | 126 List<ParameterSpec> parameterSpecs = new ArrayList<>(); |
127 parameterSpecs.addAll(methodSpecification.getParameters()); | 127 parameterSpecs.addAll(methodSpecification.getParameters()); |
128 | 128 |
129 ActualParameter returnTypeMirror = resolveTypeMirror(returnTypeSpec, method.getReturnType(), template); | 129 ActualParameter returnTypeMirror = matchParameter(returnTypeSpec, method.getReturnType(), template, 0); |
130 if (returnTypeMirror == null) { | 130 if (returnTypeMirror == null) { |
131 if (isEmitErrors()) { | 131 if (isEmitErrors()) { |
132 String expectedReturnType = createTypeSignature(returnTypeSpec, typeDefs, true); | 132 String expectedReturnType = createTypeSignature(returnTypeSpec, typeDefs, true); |
133 String actualReturnType = Utils.getSimpleName(method.getReturnType()); | 133 String actualReturnType = Utils.getSimpleName(method.getReturnType()); |
134 | 134 |
138 context.getLog().error(method, annotation, message); | 138 context.getLog().error(method, annotation, message); |
139 } | 139 } |
140 return null; | 140 return null; |
141 } | 141 } |
142 | 142 |
143 Iterator<? extends VariableElement> variableIterator = method.getParameters().iterator(); | 143 List<ActualParameter> parameters = parseParameters(method, parameterSpecs); |
144 if (parameters == null) { | |
145 if (isEmitErrors()) { | |
146 String message = String.format("Method signature mismatch. Expected signature: \n%s", | |
147 createExpectedSignature(method.getSimpleName().toString(), returnTypeSpec, parameterSpecs, typeDefs)); | |
148 context.getLog().error(method, annotation, message); | |
149 } | |
150 return null; | |
151 } | |
152 ActualParameter[] paramMirrors = parameters.toArray(new ActualParameter[parameters.size()]); | |
153 return create(new TemplateMethod(template, methodSpecification, method, annotation, returnTypeMirror, paramMirrors)); | |
154 } | |
155 | |
156 private List<ActualParameter> parseParameters(ExecutableElement method, List<ParameterSpec> parameterSpecs) { | |
157 Iterator<? extends VariableElement> parameterIterator = method.getParameters().iterator(); | |
144 Iterator<? extends ParameterSpec> specificationIterator = parameterSpecs.iterator(); | 158 Iterator<? extends ParameterSpec> specificationIterator = parameterSpecs.iterator(); |
145 | 159 |
146 List<ActualParameter> resolvedMirrors = new ArrayList<>(); | 160 VariableElement parameter = parameterIterator.hasNext() ? parameterIterator.next() : null; |
147 VariableElement parameter = null; | 161 ParameterSpec specification = specificationIterator.hasNext() ? specificationIterator.next() : null; |
148 ParameterSpec specification = null; | 162 |
149 while (specificationIterator.hasNext() || specification != null) { | 163 int specificationIndex = 0; |
150 if (specification == null) { | 164 List<ActualParameter> resolvedParameters = new ArrayList<>(); |
151 specification = specificationIterator.next(); | 165 while (parameter != null || specification != null) { |
152 } | 166 if (parameter == null || specification == null) { |
153 | 167 if (specification != null && (specification.isOptional() || specification.getCardinality() == Cardinality.MULTIPLE)) { |
154 if (parameter == null && variableIterator.hasNext()) { | 168 specification = specificationIterator.hasNext() ? specificationIterator.next() : null; |
155 parameter = variableIterator.next(); | 169 specificationIndex = 0; |
156 } | |
157 | |
158 if (parameter == null) { | |
159 if (specification.getCardinality() == Cardinality.MULTIPLE) { | |
160 specification = null; | |
161 continue; | 170 continue; |
162 } else if (!specification.isOptional()) { | 171 } |
163 if (isEmitErrors()) { | 172 return null; |
164 // non option type specification found -> argument missing | 173 } |
165 String expectedType = createTypeSignature(specification, typeDefs, false); | 174 |
166 | 175 ActualParameter resolvedParameter = matchParameter(specification, parameter.asType(), template, specificationIndex); |
167 String message = String.format("Missing argument \"%s\".\nExpected signature: \n %s", expectedType, | 176 if (resolvedParameter == null) { |
168 createExpectedSignature(method.getSimpleName().toString(), returnTypeSpec, parameterSpecs, typeDefs)); | 177 // mismatch |
169 | 178 if (specification.isOptional()) { |
170 context.getLog().error(method, message); | 179 specification = specificationIterator.hasNext() ? specificationIterator.next() : null; |
171 } | 180 specificationIndex = 0; |
181 } else { | |
172 return null; | 182 return null; |
173 } else { | 183 } |
174 // specification is optional -> continue | 184 } else { |
175 specification = null; | 185 resolvedParameters.add(resolvedParameter); |
176 continue; | 186 |
177 } | 187 // match |
178 } | 188 if (specification.getCardinality() == Cardinality.ONE) { |
179 | 189 parameter = parameterIterator.hasNext() ? parameterIterator.next() : null; |
180 ActualParameter resolvedMirror = resolveTypeMirror(specification, parameter.asType(), template); | 190 specification = specificationIterator.hasNext() ? specificationIterator.next() : null; |
181 | 191 specificationIndex = 0; |
182 if (resolvedMirror == null) { | 192 } else if (specification.getCardinality() == Cardinality.MULTIPLE) { |
183 if (specification.isOptional()) { | 193 parameter = parameterIterator.hasNext() ? parameterIterator.next() : null; |
184 specification = null; | 194 specificationIndex++; |
185 continue; | 195 } |
186 } | 196 } |
187 | 197 } |
188 if (isEmitErrors()) { | 198 return resolvedParameters; |
189 String expectedReturnType = createTypeSignature(specification, typeDefs, false); | 199 } |
190 String actualReturnType = Utils.getSimpleName(parameter.asType()) + " " + parameter.getSimpleName(); | 200 |
191 | 201 private ActualParameter matchParameter(ParameterSpec specification, TypeMirror mirror, Template typeSystem, int index) { |
192 String message = String.format("The provided argument type \"%s\" does not match expected type \"%s\".\nExpected signature: \n %s", actualReturnType, expectedReturnType, | |
193 createExpectedSignature(method.getSimpleName().toString(), returnTypeSpec, parameterSpecs, typeDefs)); | |
194 | |
195 context.getLog().error(parameter, message); | |
196 } | |
197 return null; | |
198 } | |
199 | |
200 resolvedMirrors.add(resolvedMirror); | |
201 parameter = null; // consume parameter | |
202 | |
203 if (specification.getCardinality() != Cardinality.MULTIPLE) { | |
204 specification = null; | |
205 } | |
206 } | |
207 | |
208 if (variableIterator.hasNext()) { | |
209 parameter = variableIterator.next(); | |
210 if (isEmitErrors()) { | |
211 String actualReturnType = Utils.getSimpleName(parameter.asType()) + " " + parameter.getSimpleName(); | |
212 String message = String.format("No argument expected but found \"%s\".\nExpected signature: \n %s", actualReturnType, | |
213 createExpectedSignature(method.getSimpleName().toString(), returnTypeSpec, parameterSpecs, typeDefs)); | |
214 | |
215 context.getLog().error(parameter, message); | |
216 } | |
217 return null; | |
218 } | |
219 | |
220 ActualParameter[] paramMirrors = resolvedMirrors.toArray(new ActualParameter[resolvedMirrors.size()]); | |
221 return create(new TemplateMethod(template, methodSpecification, method, annotation, returnTypeMirror, paramMirrors)); | |
222 } | |
223 | |
224 private ActualParameter resolveTypeMirror(ParameterSpec specification, TypeMirror mirror, Template typeSystem) { | |
225 TypeMirror resolvedType = mirror; | 202 TypeMirror resolvedType = mirror; |
226 if (hasError(resolvedType)) { | 203 if (hasError(resolvedType)) { |
227 resolvedType = context.resolveNotYetCompiledType(mirror, typeSystem); | 204 resolvedType = context.resolveNotYetCompiledType(mirror, typeSystem); |
228 } | 205 } |
229 | 206 |
230 if (!specification.matches(resolvedType)) { | 207 if (!specification.matches(resolvedType)) { |
231 return null; | 208 return null; |
232 } | 209 } |
233 return new ActualParameter(specification, resolvedType); | 210 return new ActualParameter(specification, resolvedType, index); |
234 } | 211 } |
235 | 212 |
236 protected List<TypeDef> createTypeDefinitions(ParameterSpec returnType, List<? extends ParameterSpec> parameters) { | 213 protected List<TypeDef> createTypeDefinitions(ParameterSpec returnType, List<? extends ParameterSpec> parameters) { |
237 List<TypeDef> typeDefs = new ArrayList<>(); | 214 List<TypeDef> typeDefs = new ArrayList<>(); |
238 | 215 |