OLD | NEW |
---|---|
1 // Copyright (c) 2012, the Dart project authors. Please see the AUTHORS file | 1 // Copyright (c) 2012, the Dart project authors. Please see the AUTHORS file |
2 // for details. All rights reserved. Use of this source code is governed by a | 2 // for details. All rights reserved. Use of this source code is governed by a |
3 // BSD-style license that can be found in the LICENSE file. | 3 // BSD-style license that can be found in the LICENSE file. |
4 | 4 |
5 #library('native'); | 5 #library('native'); |
6 #import('dart:uri'); | 6 #import('dart:uri'); |
7 #import('leg.dart'); | 7 #import('leg.dart'); |
8 #import('elements/elements.dart'); | 8 #import('elements/elements.dart'); |
9 #import('js_backend/js_backend.dart'); | 9 #import('js_backend/js_backend.dart'); |
10 #import('scanner/scannerlib.dart'); | 10 #import('scanner/scannerlib.dart'); |
(...skipping 227 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
238 FunctionSignature parameters = element.computeSignature(builder.compiler); | 238 FunctionSignature parameters = element.computeSignature(builder.compiler); |
239 if (!hasBody) { | 239 if (!hasBody) { |
240 List<String> arguments = <String>[]; | 240 List<String> arguments = <String>[]; |
241 List<HInstruction> inputs = <HInstruction>[]; | 241 List<HInstruction> inputs = <HInstruction>[]; |
242 String receiver = ''; | 242 String receiver = ''; |
243 if (element.isInstanceMember()) { | 243 if (element.isInstanceMember()) { |
244 receiver = '#.'; | 244 receiver = '#.'; |
245 inputs.add(builder.localsHandler.readThis()); | 245 inputs.add(builder.localsHandler.readThis()); |
246 } | 246 } |
247 parameters.forEachParameter((Element parameter) { | 247 parameters.forEachParameter((Element parameter) { |
248 Type type = parameter.computeType(compiler); | 248 Type type = parameter.computeType(compiler).unalias(compiler); |
249 HInstruction input = builder.localsHandler.readLocal(parameter); | 249 HInstruction input = builder.localsHandler.readLocal(parameter); |
250 if (type is FunctionType) input = convertDartClosure(parameter, type); | 250 if (type is FunctionType) { |
251 // The parameter type is a function type either directly or through | |
252 // typedef(s). | |
253 input = convertDartClosure(parameter, type); | |
ahe
2012/08/16 13:22:58
I suspect that we want to pass the unaliased type
Johnni Winther
2012/08/17 11:15:19
It seems that what is need is the arity, which imp
| |
254 } | |
251 inputs.add(input); | 255 inputs.add(input); |
252 arguments.add('#'); | 256 arguments.add('#'); |
253 }); | 257 }); |
254 | 258 |
255 String foreignParameters = Strings.join(arguments, ','); | 259 String foreignParameters = Strings.join(arguments, ','); |
256 String nativeMethodCall; | 260 String nativeMethodCall; |
257 if (element.kind == ElementKind.FUNCTION) { | 261 if (element.kind == ElementKind.FUNCTION) { |
258 nativeMethodCall = '$receiver$nativeMethodName($foreignParameters)'; | 262 nativeMethodCall = '$receiver$nativeMethodName($foreignParameters)'; |
259 } else if (element.kind == ElementKind.GETTER) { | 263 } else if (element.kind == ElementKind.GETTER) { |
260 nativeMethodCall = '$receiver$nativeMethodName'; | 264 nativeMethodCall = '$receiver$nativeMethodName'; |
261 } else if (element.kind == ElementKind.SETTER) { | 265 } else if (element.kind == ElementKind.SETTER) { |
262 nativeMethodCall = '$receiver$nativeMethodName = $foreignParameters'; | 266 nativeMethodCall = '$receiver$nativeMethodName = $foreignParameters'; |
263 } else { | 267 } else { |
264 builder.compiler.internalError('unexpected kind: "${element.kind}"', | 268 builder.compiler.internalError('unexpected kind: "${element.kind}"', |
265 element: element); | 269 element: element); |
266 } | 270 } |
267 | 271 |
268 DartString jsCode = new DartString.literal(nativeMethodCall); | 272 DartString jsCode = new DartString.literal(nativeMethodCall); |
269 builder.push( | 273 builder.push( |
270 new HForeign(jsCode, const LiteralDartString('Object'), inputs)); | 274 new HForeign(jsCode, const LiteralDartString('Object'), inputs)); |
271 builder.close(new HReturn(builder.pop())).addSuccessor(builder.graph.exit); | 275 builder.close(new HReturn(builder.pop())).addSuccessor(builder.graph.exit); |
272 } else { | 276 } else { |
273 // This is JS code written in a Dart file with the construct | 277 // This is JS code written in a Dart file with the construct |
274 // native """ ... """;. It does not work well with mangling, | 278 // native """ ... """;. It does not work well with mangling, |
275 // but there should currently be no clash between leg mangling | 279 // but there should currently be no clash between leg mangling |
276 // and the library where this construct is being used. This | 280 // and the library where this construct is being used. This |
277 // mangling problem will go away once we switch these libraries | 281 // mangling problem will go away once we switch these libraries |
278 // to use Leg's 'JS' function. | 282 // to use Leg's 'JS' function. |
279 parameters.forEachParameter((Element parameter) { | 283 parameters.forEachParameter((Element parameter) { |
280 Type type = parameter.computeType(compiler); | 284 Type type = parameter.computeType(compiler).unalias(compiler); |
281 if (type is FunctionType) { | 285 if (type is FunctionType) { |
286 // The parameter type is a function type either directly or through | |
287 // typedef(s). | |
282 HInstruction jsClosure = convertDartClosure(parameter, type); | 288 HInstruction jsClosure = convertDartClosure(parameter, type); |
283 // Because the JS code references the argument name directly, | 289 // Because the JS code references the argument name directly, |
284 // we must keep the name and assign the JS closure to it. | 290 // we must keep the name and assign the JS closure to it. |
285 builder.add(new HForeign( | 291 builder.add(new HForeign( |
286 new DartString.literal('${parameter.name.slowToString()} = #'), | 292 new DartString.literal('${parameter.name.slowToString()} = #'), |
287 const LiteralDartString('void'), | 293 const LiteralDartString('void'), |
288 <HInstruction>[jsClosure])); | 294 <HInstruction>[jsClosure])); |
289 } | 295 } |
290 }); | 296 }); |
291 LiteralString jsCode = nativeBody.asLiteralString(); | 297 LiteralString jsCode = nativeBody.asLiteralString(); |
(...skipping 38 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
330 String parameters) { | 336 String parameters) { |
331 buffer.add(" if (Object.getPrototypeOf(this).hasOwnProperty"); | 337 buffer.add(" if (Object.getPrototypeOf(this).hasOwnProperty"); |
332 buffer.add("('$methodName')) {\n"); | 338 buffer.add("('$methodName')) {\n"); |
333 buffer.add(" $code"); | 339 buffer.add(" $code"); |
334 buffer.add(" } else {\n"); | 340 buffer.add(" } else {\n"); |
335 buffer.add(" return Object.prototype.$methodName.call(this"); | 341 buffer.add(" return Object.prototype.$methodName.call(this"); |
336 buffer.add(parameters == '' ? '' : ', $parameters'); | 342 buffer.add(parameters == '' ? '' : ', $parameters'); |
337 buffer.add(");\n"); | 343 buffer.add(");\n"); |
338 buffer.add(" }\n"); | 344 buffer.add(" }\n"); |
339 } | 345 } |
OLD | NEW |