| 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 import '../common/codegen.dart' show CodegenRegistry, CodegenWorkItem; | 5 import '../common/codegen.dart' show CodegenRegistry, CodegenWorkItem; |
| 6 import '../common/names.dart' show Selectors; | 6 import '../common/names.dart' show Selectors; |
| 7 import '../common/tasks.dart' show CompilerTask; | 7 import '../common/tasks.dart' show CompilerTask; |
| 8 import '../compiler.dart' show Compiler; | 8 import '../compiler.dart' show Compiler; |
| 9 import '../constants/constant_system.dart'; | 9 import '../constants/constant_system.dart'; |
| 10 import '../constants/values.dart'; | 10 import '../constants/values.dart'; |
| 11 import '../common_elements.dart' show CommonElements; | 11 import '../common_elements.dart' show CommonElements; |
| 12 import '../elements/elements.dart' show ClassElement, MethodElement; | 12 import '../elements/elements.dart' show ClassElement; |
| 13 import '../elements/entities.dart'; | 13 import '../elements/entities.dart'; |
| 14 import '../elements/resolution_types.dart'; | 14 import '../elements/resolution_types.dart'; |
| 15 import '../elements/types.dart'; | 15 import '../elements/types.dart'; |
| 16 import '../js/js.dart' as js; | 16 import '../js/js.dart' as js; |
| 17 import '../js_backend/backend.dart'; | 17 import '../js_backend/backend.dart'; |
| 18 import '../js_backend/native_data.dart' show NativeData; | 18 import '../js_backend/native_data.dart' show NativeData; |
| 19 import '../js_backend/runtime_types.dart'; | 19 import '../js_backend/runtime_types.dart'; |
| 20 import '../native/native.dart' as native; | 20 import '../native/native.dart' as native; |
| 21 import '../options.dart'; | 21 import '../options.dart'; |
| 22 import '../types/types.dart'; | 22 import '../types/types.dart'; |
| (...skipping 501 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 524 ..sourceInformation = node.sourceInformation; | 524 ..sourceInformation = node.sourceInformation; |
| 525 node.block.addAfter(load, closureCall); | 525 node.block.addAfter(load, closureCall); |
| 526 return closureCall; | 526 return closureCall; |
| 527 } | 527 } |
| 528 } | 528 } |
| 529 | 529 |
| 530 return node; | 530 return node; |
| 531 } | 531 } |
| 532 | 532 |
| 533 HInstruction tryInlineNativeMethod( | 533 HInstruction tryInlineNativeMethod( |
| 534 HInvokeDynamicMethod node, MethodElement method) { | 534 HInvokeDynamicMethod node, FunctionEntity method) { |
| 535 // Enable direct calls to a native method only if we don't run in checked | 535 // Enable direct calls to a native method only if we don't run in checked |
| 536 // mode, where the Dart version may have type annotations on parameters and | 536 // mode, where the Dart version may have type annotations on parameters and |
| 537 // return type that it should check. | 537 // return type that it should check. |
| 538 // Also check that the parameters are not functions: it's the callee that | 538 // Also check that the parameters are not functions: it's the callee that |
| 539 // will translate them to JS functions. | 539 // will translate them to JS functions. |
| 540 // | 540 // |
| 541 // TODO(ngeoffray): There are some cases where we could still inline in | 541 // TODO(ngeoffray): There are some cases where we could still inline in |
| 542 // checked mode if we know the arguments have the right type. And we could | 542 // checked mode if we know the arguments have the right type. And we could |
| 543 // do the closure conversion as well as the return type annotation check. | 543 // do the closure conversion as well as the return type annotation check. |
| 544 | 544 |
| 545 if (!node.isInterceptedCall) return null; | 545 if (!node.isInterceptedCall) return null; |
| 546 | 546 |
| 547 // TODO(sra): Check for legacy methods with bodies in the native strings. | 547 FunctionType type = _closedWorld.elementEnvironment.getFunctionType(method); |
| 548 // foo() native 'return something'; | |
| 549 // They should not be used. | |
| 550 | |
| 551 ResolutionFunctionType type = method.type; | |
| 552 if (type.namedParameters.isNotEmpty) return null; | 548 if (type.namedParameters.isNotEmpty) return null; |
| 553 | 549 |
| 554 // Return types on native methods don't need to be checked, since the | 550 // Return types on native methods don't need to be checked, since the |
| 555 // declaration has to be truthful. | 551 // declaration has to be truthful. |
| 556 | 552 |
| 557 // The call site might omit optional arguments. The inlined code must | 553 // The call site might omit optional arguments. The inlined code must |
| 558 // preserve the number of arguments, so check only the actual arguments. | 554 // preserve the number of arguments, so check only the actual arguments. |
| 559 | 555 |
| 560 List<HInstruction> inputs = node.inputs.sublist(1); | 556 List<HInstruction> inputs = node.inputs.sublist(1); |
| 561 bool canInline = true; | 557 bool canInline = true; |
| 562 if (_options.enableTypeAssertions && inputs.length > 1) { | 558 if (_options.enableTypeAssertions && inputs.length > 1) { |
| 563 // TODO(sra): Check if [input] is guaranteed to pass the parameter | 559 // TODO(sra): Check if [input] is guaranteed to pass the parameter |
| 564 // type check. Consider using a strengthened type check to avoid | 560 // type check. Consider using a strengthened type check to avoid |
| 565 // passing `null` to primitive types since the native methods usually | 561 // passing `null` to primitive types since the native methods usually |
| 566 // have non-nullable primitive parameter types. | 562 // have non-nullable primitive parameter types. |
| 567 canInline = false; | 563 canInline = false; |
| 568 } else { | 564 } else { |
| 569 int inputPosition = 1; // Skip receiver. | 565 int inputPosition = 1; // Skip receiver. |
| 570 void checkParameterType(ResolutionDartType type) { | 566 void checkParameterType(DartType type) { |
| 571 if (inputPosition++ < inputs.length && canInline) { | 567 if (inputPosition++ < inputs.length && canInline) { |
| 572 if (type.unaliased.isFunctionType) { | 568 if (type.unaliased.isFunctionType) { |
| 573 canInline = false; | 569 canInline = false; |
| 574 } | 570 } |
| 575 } | 571 } |
| 576 } | 572 } |
| 577 | 573 |
| 578 type.parameterTypes.forEach(checkParameterType); | 574 type.parameterTypes.forEach(checkParameterType); |
| 579 type.optionalParameterTypes.forEach(checkParameterType); | 575 type.optionalParameterTypes.forEach(checkParameterType); |
| 580 type.namedParameterTypes.forEach(checkParameterType); | 576 type.namedParameterTypes.forEach(checkParameterType); |
| (...skipping 2408 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 2989 | 2985 |
| 2990 keyedValues.forEach((receiver, values) { | 2986 keyedValues.forEach((receiver, values) { |
| 2991 result.keyedValues[receiver] = | 2987 result.keyedValues[receiver] = |
| 2992 new Map<HInstruction, HInstruction>.from(values); | 2988 new Map<HInstruction, HInstruction>.from(values); |
| 2993 }); | 2989 }); |
| 2994 | 2990 |
| 2995 result.nonEscapingReceivers.addAll(nonEscapingReceivers); | 2991 result.nonEscapingReceivers.addAll(nonEscapingReceivers); |
| 2996 return result; | 2992 return result; |
| 2997 } | 2993 } |
| 2998 } | 2994 } |
| OLD | NEW |