Chromium Code Reviews| 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 part of js_backend; | 5 part of js_backend; |
| 6 | 6 |
| 7 typedef void Recompile(Element element); | 7 typedef void Recompile(Element element); |
| 8 | 8 |
| 9 class ReturnInfo { | 9 class ReturnInfo { |
| 10 HType returnType; | 10 HType returnType; |
| (...skipping 594 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 605 } | 605 } |
| 606 } | 606 } |
| 607 | 607 |
| 608 class JavaScriptItemCompilationContext extends ItemCompilationContext { | 608 class JavaScriptItemCompilationContext extends ItemCompilationContext { |
| 609 final Set<HInstruction> boundsChecked; | 609 final Set<HInstruction> boundsChecked; |
| 610 | 610 |
| 611 JavaScriptItemCompilationContext() | 611 JavaScriptItemCompilationContext() |
| 612 : boundsChecked = new Set<HInstruction>(); | 612 : boundsChecked = new Set<HInstruction>(); |
| 613 } | 613 } |
| 614 | 614 |
| 615 | |
| 616 class CheckedModeHelper { | |
| 617 final SourceString name; | |
| 618 | |
| 619 const CheckedModeHelper(SourceString this.name); | |
| 620 | |
| 621 Element getElement(Compiler compiler) => compiler.findHelper(name); | |
| 622 | |
| 623 jsAst.Expression generateCall(SsaCodeGenerator codegen, | |
| 624 HTypeConversion node) { | |
| 625 Element helperElement = getElement(codegen.compiler); | |
| 626 codegen.world.registerStaticUse(helperElement); | |
| 627 List<jsAst.Expression> arguments = <jsAst.Expression>[]; | |
| 628 codegen.use(node.checkedInput); | |
| 629 arguments.add(codegen.pop()); | |
| 630 generateAdditionalArguments(codegen, node, arguments); | |
| 631 String helperName = codegen.backend.namer.isolateAccess(helperElement); | |
| 632 return new jsAst.Call(new jsAst.VariableUse(helperName), arguments); | |
| 633 } | |
| 634 | |
| 635 void generateAdditionalArguments(SsaCodeGenerator codegen, | |
| 636 HTypeConversion node, | |
| 637 List<jsAst.Expression> arguments) { | |
| 638 assert(!node.typeExpression.isMalformed); | |
| 639 // No additional arguments needed. | |
| 640 } | |
| 641 } | |
| 642 | |
| 643 class PropertyCheckedModeHelper extends CheckedModeHelper { | |
| 644 const PropertyCheckedModeHelper(SourceString name) : super(name); | |
| 645 | |
| 646 void generateAdditionalArguments(SsaCodeGenerator codegen, | |
| 647 HTypeConversion node, | |
| 648 List<jsAst.Expression> arguments) { | |
| 649 DartType type = node.typeExpression; | |
| 650 assert(!type.isMalformed); | |
| 651 String additionalArgument = codegen.backend.namer.operatorIsType(type); | |
| 652 arguments.add(js.string(additionalArgument)); | |
| 653 } | |
| 654 } | |
| 655 | |
| 656 class TypeVariableCheckedModeHelper extends CheckedModeHelper { | |
| 657 const TypeVariableCheckedModeHelper(SourceString name) : super(name); | |
| 658 | |
| 659 void generateAdditionalArguments(SsaCodeGenerator codegen, | |
| 660 HTypeConversion node, | |
| 661 List<jsAst.Expression> arguments) { | |
| 662 assert(node.typeExpression.kind == TypeKind.TYPE_VARIABLE); | |
| 663 codegen.use(node.typeRepresentation); | |
| 664 arguments.add(codegen.pop()); | |
| 665 } | |
| 666 } | |
| 667 | |
| 668 class SubtypeCheckedModeHelper extends CheckedModeHelper { | |
| 669 const SubtypeCheckedModeHelper(SourceString name) : super(name); | |
| 670 | |
| 671 void generateAdditionalArguments(SsaCodeGenerator codegen, | |
| 672 HTypeConversion node, | |
| 673 List<jsAst.Expression> arguments) { | |
| 674 DartType type = node.typeExpression; | |
| 675 Element element = type.element; | |
| 676 String isField = codegen.backend.namer.operatorIs(element); | |
| 677 arguments.add(js.string(isField)); | |
| 678 codegen.use(node.typeRepresentation); | |
| 679 arguments.add(codegen.pop()); | |
| 680 String asField = codegen.backend.namer.substitutionName(element); | |
| 681 arguments.add(js.string(asField)); | |
| 682 } | |
| 683 } | |
| 684 | |
| 685 class FunctionTypeCheckedModeHelper extends CheckedModeHelper { | |
| 686 const FunctionTypeCheckedModeHelper(SourceString name) : super(name); | |
| 687 | |
| 688 void generateAdditionalArguments(SsaCodeGenerator codegen, | |
| 689 HTypeConversion node, | |
| 690 List<jsAst.Expression> arguments) { | |
| 691 DartType type = node.typeExpression; | |
| 692 String signatureName = codegen.backend.namer.getFunctionTypeName(type); | |
| 693 arguments.add(js.string(signatureName)); | |
| 694 | |
| 695 if (type.containsTypeVariables) { | |
| 696 ClassElement contextClass = Types.getClassContext(type); | |
| 697 String contextName = codegen.backend.namer.getName(contextClass); | |
| 698 arguments.add(js.string(contextName)); | |
| 699 | |
| 700 if (node.contextIsTypeArguments) { | |
| 701 arguments.add(new jsAst.LiteralNull()); | |
| 702 codegen.use(node.context); | |
| 703 arguments.add(codegen.pop()); | |
| 704 } else { | |
| 705 codegen.use(node.context); | |
| 706 arguments.add(codegen.pop()); | |
| 707 } | |
| 708 } | |
| 709 } | |
| 710 } | |
| 711 | |
| 712 class MalformedCheckedModeHelper extends CheckedModeHelper { | |
| 713 const MalformedCheckedModeHelper(SourceString name) : super(name); | |
| 714 | |
| 715 void generateAdditionalArguments(SsaCodeGenerator codegen, | |
| 716 HTypeConversion node, | |
| 717 List<jsAst.Expression> arguments) { | |
| 718 DartType type = node.typeExpression; | |
| 719 assert(type.isMalformed); | |
| 720 String reasons = Types.fetchReasonsFromMalformedType(type); | |
| 721 arguments.add(js.string('$type')); | |
| 722 // TODO(johnniwinther): Handle escaping correctly. | |
| 723 arguments.add(js.string(reasons)); | |
| 724 } | |
| 725 } | |
| 726 | |
| 727 | |
| 615 class JavaScriptBackend extends Backend { | 728 class JavaScriptBackend extends Backend { |
| 616 SsaBuilderTask builder; | 729 SsaBuilderTask builder; |
| 617 SsaOptimizerTask optimizer; | 730 SsaOptimizerTask optimizer; |
| 618 SsaCodeGeneratorTask generator; | 731 SsaCodeGeneratorTask generator; |
| 619 CodeEmitterTask emitter; | 732 CodeEmitterTask emitter; |
| 620 | 733 |
| 621 /** | 734 /** |
| 622 * The generated code as a js AST for compiled methods. | 735 * The generated code as a js AST for compiled methods. |
| 623 */ | 736 */ |
| 624 Map<Element, jsAst.Expression> get generatedCode { | 737 Map<Element, jsAst.Expression> get generatedCode { |
| (...skipping 594 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 1219 } | 1332 } |
| 1220 | 1333 |
| 1221 void registerSetRuntimeType(TreeElements elements) { | 1334 void registerSetRuntimeType(TreeElements elements) { |
| 1222 enqueueInResolution(getSetRuntimeTypeInfo(), elements); | 1335 enqueueInResolution(getSetRuntimeTypeInfo(), elements); |
| 1223 } | 1336 } |
| 1224 | 1337 |
| 1225 void registerGetRuntimeTypeArgument(TreeElements elements) { | 1338 void registerGetRuntimeTypeArgument(TreeElements elements) { |
| 1226 enqueueInResolution(getGetRuntimeTypeArgument(), elements); | 1339 enqueueInResolution(getGetRuntimeTypeArgument(), elements); |
| 1227 } | 1340 } |
| 1228 | 1341 |
| 1229 void registerRuntimeType(TreeElements elements) { | 1342 void registerGenericCallMethod(Element callMethod, |
| 1343 Enqueuer enqueuer, TreeElements elements) { | |
| 1344 if (enqueuer.isResolutionQueue || methodNeedsRti(callMethod)) { | |
| 1345 registerApplySignature(enqueuer, elements); | |
| 1346 } | |
| 1347 } | |
| 1348 | |
| 1349 void registerGenericClosure(Element closure, | |
| 1350 Enqueuer enqueuer, TreeElements elements) { | |
| 1351 if (enqueuer.isResolutionQueue || methodNeedsRti(closure)) { | |
| 1352 registerApplySignature(enqueuer, elements); | |
| 1353 } | |
| 1354 } | |
| 1355 | |
| 1356 void registerApplySignature(Enqueuer enqueuer, TreeElements elements) { | |
| 1357 // Calls to [:applySignature:] are generated by the emitter and we therefore | |
| 1358 // need to enqueue the used elements in the codegen enqueuer as well as in | |
| 1359 // the resolution enqueuer. | |
| 1360 enqueue(enqueuer, getSetRuntimeTypeInfo(), elements); | |
| 1361 enqueue(enqueuer, getGetRuntimeTypeInfo(), elements); | |
| 1362 enqueue(enqueuer, getApplySignature(), elements); | |
| 1363 enqueue(enqueuer, getGetRuntimeTypeArguments(), elements); | |
| 1364 enqueuer.registerInstantiatedClass(compiler.listClass, elements); | |
| 1365 } | |
| 1366 | |
| 1367 void registerRuntimeType(Enqueuer enqueuer, TreeElements elements) { | |
| 1368 registerApplySignature(enqueuer, elements); | |
| 1230 enqueueInResolution(getSetRuntimeTypeInfo(), elements); | 1369 enqueueInResolution(getSetRuntimeTypeInfo(), elements); |
| 1231 enqueueInResolution(getGetRuntimeTypeInfo(), elements); | 1370 enqueueInResolution(getGetRuntimeTypeInfo(), elements); |
| 1232 enqueueInResolution(getGetRuntimeTypeArgument(), elements); | 1371 registerGetRuntimeTypeArgument(elements); |
| 1233 compiler.enqueuer.resolution.registerInstantiatedClass( | 1372 compiler.enqueuer.resolution.registerInstantiatedClass( |
| 1234 compiler.listClass, elements); | 1373 compiler.listClass, elements); |
| 1235 } | 1374 } |
| 1236 | 1375 |
| 1237 void registerTypeVariableExpression(TreeElements elements) { | 1376 void registerTypeVariableExpression(TreeElements elements) { |
| 1238 registerRuntimeType(elements); | 1377 enqueueInResolution(getSetRuntimeTypeInfo(), elements); |
| 1378 enqueueInResolution(getGetRuntimeTypeInfo(), elements); | |
| 1379 registerGetRuntimeTypeArgument(elements); | |
| 1380 compiler.enqueuer.resolution.registerInstantiatedClass( | |
| 1381 compiler.listClass, elements); | |
| 1239 enqueueInResolution(getRuntimeTypeToString(), elements); | 1382 enqueueInResolution(getRuntimeTypeToString(), elements); |
| 1240 enqueueInResolution(getCreateRuntimeType(), elements); | 1383 enqueueInResolution(getCreateRuntimeType(), elements); |
| 1241 } | 1384 } |
| 1242 | 1385 |
| 1243 void registerIsCheck(DartType type, Enqueuer world, TreeElements elements) { | 1386 void registerIsCheck(DartType type, Enqueuer world, TreeElements elements) { |
| 1244 world.registerInstantiatedClass(compiler.boolClass, elements); | 1387 world.registerInstantiatedClass(compiler.boolClass, elements); |
| 1388 bool inCheckedMode = compiler.enableTypeAssertions; | |
| 1389 // [registerIsCheck] is also called for checked mode checks, so we | |
| 1390 // need to register checked mode helpers. | |
| 1391 if (inCheckedMode) { | |
| 1392 CheckedModeHelper helper = getCheckedModeHelper(type, typeCast: false); | |
| 1393 if (helper != null) world.addToWorkList(helper.getElement(compiler)); | |
| 1394 // We also need the native variant of the check (for DOM types). | |
| 1395 helper = getNativeCheckedModeHelper(type, typeCast: false); | |
| 1396 if (helper != null) world.addToWorkList(helper.getElement(compiler)); | |
| 1397 if (type.isMalformed) { | |
| 1398 enqueueInResolution(getThrowMalformedSubtypeError(), elements); | |
| 1399 return; | |
| 1400 } | |
| 1401 } else { | |
| 1402 if (type.isMalformed) { | |
| 1403 registerThrowRuntimeError(elements); | |
| 1404 return; | |
| 1405 } | |
| 1406 } | |
| 1407 if (type.element.isNative()) { | |
| 1408 // We will neeed to add the "$is" and "$as" properties on the | |
| 1409 // JavaScript object prototype, so we make sure | |
| 1410 // [:defineProperty:] is compiled. | |
| 1411 world.addToWorkList( | |
| 1412 compiler.findHelper(const SourceString('defineProperty'))); | |
|
karlklose
2013/06/19 14:37:05
Why is that necessary? Shouldn't it be enough to r
Johnni Winther
2013/06/21 12:19:15
I have no idea. The code was just moved from below
| |
| 1413 } | |
| 1245 bool isTypeVariable = type.kind == TypeKind.TYPE_VARIABLE; | 1414 bool isTypeVariable = type.kind == TypeKind.TYPE_VARIABLE; |
| 1246 bool inCheckedMode = compiler.enableTypeAssertions; | 1415 if (!type.isRaw || type.containsTypeVariables) { |
| 1247 if (!type.isRaw || isTypeVariable) { | |
| 1248 enqueueInResolution(getSetRuntimeTypeInfo(), elements); | 1416 enqueueInResolution(getSetRuntimeTypeInfo(), elements); |
| 1249 enqueueInResolution(getGetRuntimeTypeInfo(), elements); | 1417 enqueueInResolution(getGetRuntimeTypeInfo(), elements); |
| 1250 enqueueInResolution(getGetRuntimeTypeArgument(), elements); | 1418 enqueueInResolution(getGetRuntimeTypeArgument(), elements); |
| 1251 if (inCheckedMode) { | 1419 if (inCheckedMode) { |
| 1252 enqueueInResolution(getAssertSubtype(), elements); | 1420 enqueueInResolution(getAssertSubtype(), elements); |
| 1253 } | 1421 } |
| 1254 enqueueInResolution(getCheckSubtype(), elements); | 1422 enqueueInResolution(getCheckSubtype(), elements); |
| 1255 if (isTypeVariable) { | 1423 if (isTypeVariable) { |
| 1256 enqueueInResolution(getCheckSubtypeOfRuntimeType(), elements); | 1424 enqueueInResolution(getCheckSubtypeOfRuntimeType(), elements); |
| 1257 if (inCheckedMode) { | 1425 if (inCheckedMode) { |
| 1258 enqueueInResolution(getAssertSubtypeOfRuntimeType(), elements); | 1426 enqueueInResolution(getAssertSubtypeOfRuntimeType(), elements); |
| 1259 } | 1427 } |
| 1260 } | 1428 } |
| 1261 world.registerInstantiatedClass(compiler.listClass, elements); | 1429 world.registerInstantiatedClass(compiler.listClass, elements); |
| 1262 } | 1430 } |
| 1263 // [registerIsCheck] is also called for checked mode checks, so we | 1431 if (type is FunctionType) { |
| 1264 // need to register checked mode helpers. | 1432 enqueueInResolution(getCheckFunctionSubtype(), elements); |
| 1265 if (inCheckedMode) { | |
| 1266 Element e = getCheckedModeHelper(type, typeCast: false); | |
| 1267 if (e != null) world.addToWorkList(e); | |
| 1268 // We also need the native variant of the check (for DOM types). | |
| 1269 e = getNativeCheckedModeHelper(type, typeCast: false); | |
| 1270 if (e != null) world.addToWorkList(e); | |
| 1271 } | 1433 } |
| 1272 if (type.element.isNative()) { | 1434 } |
| 1273 // We will neeed to add the "$is" and "$as" properties on the | 1435 |
| 1274 // JavaScript object prototype, so we make sure | 1436 void registerAsCheck(DartType type, TreeElements elements) { |
| 1275 // [:defineProperty:] is compiled. | 1437 CheckedModeHelper helper = getCheckedModeHelper(type, typeCast: true); |
| 1276 world.addToWorkList( | 1438 enqueueInResolution(helper.getElement(compiler), elements); |
| 1277 compiler.findHelper(const SourceString('defineProperty'))); | 1439 // We also need the native variant of the check (for DOM types). |
| 1440 helper = getNativeCheckedModeHelper(type, typeCast: true); | |
| 1441 if (helper != null) { | |
| 1442 enqueueInResolution(helper.getElement(compiler), elements); | |
| 1278 } | 1443 } |
| 1279 } | 1444 } |
| 1280 | 1445 |
| 1281 void registerAsCheck(DartType type, TreeElements elements) { | |
| 1282 Element e = getCheckedModeHelper(type, typeCast: true); | |
| 1283 enqueueInResolution(e, elements); | |
| 1284 // We also need the native variant of the check (for DOM types). | |
| 1285 e = getNativeCheckedModeHelper(type, typeCast: true); | |
| 1286 enqueueInResolution(e, elements); | |
| 1287 } | |
| 1288 | |
| 1289 void registerThrowNoSuchMethod(TreeElements elements) { | 1446 void registerThrowNoSuchMethod(TreeElements elements) { |
| 1290 enqueueInResolution(getThrowNoSuchMethod(), elements); | 1447 enqueueInResolution(getThrowNoSuchMethod(), elements); |
| 1291 } | 1448 } |
| 1292 | 1449 |
| 1293 void registerThrowRuntimeError(TreeElements elements) { | 1450 void registerThrowRuntimeError(TreeElements elements) { |
| 1294 enqueueInResolution(getThrowRuntimeError(), elements); | 1451 enqueueInResolution(getThrowRuntimeError(), elements); |
| 1295 } | 1452 } |
| 1296 | 1453 |
| 1297 void registerAbstractClassInstantiation(TreeElements elements) { | 1454 void registerAbstractClassInstantiation(TreeElements elements) { |
| 1298 enqueueInResolution(getThrowAbstractClassInstantiationError(), elements); | 1455 enqueueInResolution(getThrowAbstractClassInstantiationError(), elements); |
| (...skipping 61 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 1360 } | 1517 } |
| 1361 | 1518 |
| 1362 bool isDefaultEqualityImplementation(Element element) { | 1519 bool isDefaultEqualityImplementation(Element element) { |
| 1363 assert(element.name == const SourceString('==')); | 1520 assert(element.name == const SourceString('==')); |
| 1364 ClassElement classElement = element.getEnclosingClass(); | 1521 ClassElement classElement = element.getEnclosingClass(); |
| 1365 return classElement == compiler.objectClass | 1522 return classElement == compiler.objectClass |
| 1366 || classElement == jsInterceptorClass | 1523 || classElement == jsInterceptorClass |
| 1367 || classElement == jsNullClass; | 1524 || classElement == jsNullClass; |
| 1368 } | 1525 } |
| 1369 | 1526 |
| 1527 bool methodNeedsRti(Element cls) { | |
| 1528 return rti.methodsNeedingRti.contains(cls) || compiler.enabledRuntimeType; | |
| 1529 } | |
| 1530 | |
| 1531 void enqueue(Enqueuer enqueuer, Element e, TreeElements elements) { | |
| 1532 enqueuer.addToWorkList(e); | |
| 1533 elements.registerDependency(e); | |
| 1534 } | |
| 1535 | |
| 1370 void enqueueInResolution(Element e, TreeElements elements) { | 1536 void enqueueInResolution(Element e, TreeElements elements) { |
| 1371 if (e == null) return; | 1537 if (e == null) return; |
| 1372 ResolutionEnqueuer enqueuer = compiler.enqueuer.resolution; | 1538 ResolutionEnqueuer enqueuer = compiler.enqueuer.resolution; |
| 1373 enqueuer.addToWorkList(e); | 1539 enqueue(enqueuer, e, elements); |
| 1374 elements.registerDependency(e); | |
| 1375 } | 1540 } |
| 1376 | 1541 |
| 1377 void registerConstantMap(TreeElements elements) { | 1542 void registerConstantMap(TreeElements elements) { |
| 1378 Element e = compiler.findHelper(const SourceString('ConstantMap')); | 1543 Element e = compiler.findHelper(const SourceString('ConstantMap')); |
| 1379 if (e != null) { | 1544 if (e != null) { |
| 1380 compiler.enqueuer.resolution.registerInstantiatedClass(e, elements); | 1545 compiler.enqueuer.resolution.registerInstantiatedClass(e, elements); |
| 1381 } | 1546 } |
| 1382 e = compiler.findHelper(const SourceString('ConstantProtoMap')); | 1547 e = compiler.findHelper(const SourceString('ConstantProtoMap')); |
| 1383 if (e != null) { | 1548 if (e != null) { |
| 1384 compiler.enqueuer.resolution.registerInstantiatedClass(e, elements); | 1549 compiler.enqueuer.resolution.registerInstantiatedClass(e, elements); |
| (...skipping 221 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 1606 return element; | 1771 return element; |
| 1607 } | 1772 } |
| 1608 } | 1773 } |
| 1609 | 1774 |
| 1610 /** | 1775 /** |
| 1611 * Returns the checked mode helper that will be needed to do a type check/type | 1776 * Returns the checked mode helper that will be needed to do a type check/type |
| 1612 * cast on [type] at runtime. Note that this method is being called both by | 1777 * cast on [type] at runtime. Note that this method is being called both by |
| 1613 * the resolver with interface types (int, String, ...), and by the SSA | 1778 * the resolver with interface types (int, String, ...), and by the SSA |
| 1614 * backend with implementation types (JSInt, JSString, ...). | 1779 * backend with implementation types (JSInt, JSString, ...). |
| 1615 */ | 1780 */ |
| 1616 Element getCheckedModeHelper(DartType type, {bool typeCast}) { | 1781 CheckedModeHelper getCheckedModeHelper(DartType type, {bool typeCast}) { |
| 1617 SourceString name = getCheckedModeHelperName( | 1782 return getCheckedModeHelperInternal( |
| 1618 type, typeCast: typeCast, nativeCheckOnly: false); | 1783 type, typeCast: typeCast, nativeCheckOnly: false); |
| 1619 return compiler.findHelper(name); | |
| 1620 } | 1784 } |
| 1621 | 1785 |
| 1622 /** | 1786 /** |
| 1623 * Returns the native checked mode helper that will be needed to do a type | 1787 * Returns the native checked mode helper that will be needed to do a type |
| 1624 * check/type cast on [type] at runtime. If no native helper exists for | 1788 * check/type cast on [type] at runtime. If no native helper exists for |
| 1625 * [type], [:null:] is returned. | 1789 * [type], [:null:] is returned. |
| 1626 */ | 1790 */ |
| 1627 Element getNativeCheckedModeHelper(DartType type, {bool typeCast}) { | 1791 CheckedModeHelper getNativeCheckedModeHelper(DartType type, {bool typeCast}) { |
| 1628 SourceString sourceName = getCheckedModeHelperName( | 1792 return getCheckedModeHelperInternal( |
| 1629 type, typeCast: typeCast, nativeCheckOnly: true); | 1793 type, typeCast: typeCast, nativeCheckOnly: true); |
| 1630 if (sourceName == null) return null; | |
| 1631 return compiler.findHelper(sourceName); | |
| 1632 } | 1794 } |
| 1633 | 1795 |
| 1634 /** | 1796 /** |
| 1635 * Returns the name of the type check/type cast helper method for [type]. If | 1797 * Returns the checked mode helper for the type check/type cast for [type]. If |
| 1636 * [nativeCheckOnly] is [:true:], only names for native helpers are returned. | 1798 * [nativeCheckOnly] is [:true:], only names for native helpers are returned. |
| 1637 */ | 1799 */ |
| 1638 SourceString getCheckedModeHelperName(DartType type, | 1800 CheckedModeHelper getCheckedModeHelperInternal(DartType type, |
| 1639 {bool typeCast, | 1801 {bool typeCast, |
| 1640 bool nativeCheckOnly}) { | 1802 bool nativeCheckOnly}) { |
| 1641 Element element = type.element; | 1803 Element element = type.element; |
| 1642 bool nativeCheck = nativeCheckOnly || | 1804 bool nativeCheck = nativeCheckOnly || |
| 1643 emitter.nativeEmitter.requiresNativeIsCheck(element); | 1805 emitter.nativeEmitter.requiresNativeIsCheck(element); |
| 1644 if (type.isMalformed) { | 1806 if (type.isMalformed) { |
| 1645 // Check for malformed types first, because the type may be a list type | 1807 // Check for malformed types first, because the type may be a list type |
| 1646 // with a malformed argument type. | 1808 // with a malformed argument type. |
| 1647 if (nativeCheckOnly) return null; | 1809 if (nativeCheckOnly) return null; |
| 1648 return typeCast | 1810 return typeCast |
| 1649 ? const SourceString('malformedTypeCast') | 1811 ? const MalformedCheckedModeHelper(const SourceString('malformedTypeCa st')) |
| 1650 : const SourceString('malformedTypeCheck'); | 1812 : const MalformedCheckedModeHelper(const SourceString('malformedTypeCh eck')); |
| 1651 } else if (type == compiler.types.voidType) { | 1813 } else if (type == compiler.types.voidType) { |
| 1652 assert(!typeCast); // Cannot cast to void. | 1814 assert(!typeCast); // Cannot cast to void. |
| 1653 if (nativeCheckOnly) return null; | 1815 if (nativeCheckOnly) return null; |
| 1654 return const SourceString('voidTypeCheck'); | 1816 return const CheckedModeHelper(const SourceString('voidTypeCheck')); |
| 1655 } else if (element == jsStringClass || element == compiler.stringClass) { | 1817 } else if (element == jsStringClass || element == compiler.stringClass) { |
| 1656 if (nativeCheckOnly) return null; | 1818 if (nativeCheckOnly) return null; |
| 1657 return typeCast | 1819 return typeCast |
| 1658 ? const SourceString("stringTypeCast") | 1820 ? const CheckedModeHelper(const SourceString("stringTypeCast")) |
| 1659 : const SourceString('stringTypeCheck'); | 1821 : const CheckedModeHelper(const SourceString('stringTypeCheck')); |
| 1660 } else if (element == jsDoubleClass || element == compiler.doubleClass) { | 1822 } else if (element == jsDoubleClass || element == compiler.doubleClass) { |
| 1661 if (nativeCheckOnly) return null; | 1823 if (nativeCheckOnly) return null; |
| 1662 return typeCast | 1824 return typeCast |
| 1663 ? const SourceString("doubleTypeCast") | 1825 ? const CheckedModeHelper(const SourceString("doubleTypeCast")) |
| 1664 : const SourceString('doubleTypeCheck'); | 1826 : const CheckedModeHelper(const SourceString('doubleTypeCheck')); |
| 1665 } else if (element == jsNumberClass || element == compiler.numClass) { | 1827 } else if (element == jsNumberClass || element == compiler.numClass) { |
| 1666 if (nativeCheckOnly) return null; | 1828 if (nativeCheckOnly) return null; |
| 1667 return typeCast | 1829 return typeCast |
| 1668 ? const SourceString("numTypeCast") | 1830 ? const CheckedModeHelper(const SourceString("numTypeCast")) |
| 1669 : const SourceString('numTypeCheck'); | 1831 : const CheckedModeHelper(const SourceString('numTypeCheck')); |
| 1670 } else if (element == jsBoolClass || element == compiler.boolClass) { | 1832 } else if (element == jsBoolClass || element == compiler.boolClass) { |
| 1671 if (nativeCheckOnly) return null; | 1833 if (nativeCheckOnly) return null; |
| 1672 return typeCast | 1834 return typeCast |
| 1673 ? const SourceString("boolTypeCast") | 1835 ? const CheckedModeHelper(const SourceString("boolTypeCast")) |
| 1674 : const SourceString('boolTypeCheck'); | 1836 : const CheckedModeHelper(const SourceString('boolTypeCheck')); |
| 1675 } else if (element == jsIntClass || element == compiler.intClass) { | 1837 } else if (element == jsIntClass || element == compiler.intClass) { |
| 1676 if (nativeCheckOnly) return null; | 1838 if (nativeCheckOnly) return null; |
| 1677 return typeCast ? | 1839 return typeCast |
| 1678 const SourceString("intTypeCast") : | 1840 ? const CheckedModeHelper(const SourceString("intTypeCast")) |
| 1679 const SourceString('intTypeCheck'); | 1841 : const CheckedModeHelper(const SourceString('intTypeCheck')); |
| 1680 } else if (Elements.isNumberOrStringSupertype(element, compiler)) { | 1842 } else if (Elements.isNumberOrStringSupertype(element, compiler)) { |
| 1681 if (nativeCheck) { | 1843 if (nativeCheck) { |
| 1682 return typeCast | 1844 return typeCast |
| 1683 ? const SourceString("numberOrStringSuperNativeTypeCast") | 1845 ? const PropertyCheckedModeHelper(const SourceString("numberOrString SuperNativeTypeCast")) |
| 1684 : const SourceString('numberOrStringSuperNativeTypeCheck'); | 1846 : const PropertyCheckedModeHelper(const SourceString('numberOrString SuperNativeTypeCheck')); |
| 1685 } else { | 1847 } else { |
| 1686 return typeCast | 1848 return typeCast |
| 1687 ? const SourceString("numberOrStringSuperTypeCast") | 1849 ? const PropertyCheckedModeHelper(const SourceString("numberOrStringSu perTypeCast")) |
| 1688 : const SourceString('numberOrStringSuperTypeCheck'); | 1850 : const PropertyCheckedModeHelper(const SourceString('numberOrStringSu perTypeCheck')); |
| 1689 } | 1851 } |
| 1690 } else if (Elements.isStringOnlySupertype(element, compiler)) { | 1852 } else if (Elements.isStringOnlySupertype(element, compiler)) { |
| 1691 if (nativeCheck) { | 1853 if (nativeCheck) { |
| 1692 return typeCast | 1854 return typeCast |
| 1693 ? const SourceString("stringSuperNativeTypeCast") | 1855 ? const PropertyCheckedModeHelper(const SourceString("stringSuperNat iveTypeCast")) |
| 1694 : const SourceString('stringSuperNativeTypeCheck'); | 1856 : const PropertyCheckedModeHelper(const SourceString('stringSuperNat iveTypeCheck')); |
| 1695 } else { | 1857 } else { |
| 1696 return typeCast | 1858 return typeCast |
| 1697 ? const SourceString("stringSuperTypeCast") | 1859 ? const PropertyCheckedModeHelper(const SourceString("stringSuperTyp eCast")) |
| 1698 : const SourceString('stringSuperTypeCheck'); | 1860 : const PropertyCheckedModeHelper(const SourceString('stringSuperTyp eCheck')); |
| 1699 } | 1861 } |
| 1700 } else if ((element == compiler.listClass || element == jsArrayClass) && | 1862 } else if ((element == compiler.listClass || element == jsArrayClass) && |
| 1701 type.isRaw) { | 1863 type.isRaw) { |
| 1702 if (nativeCheckOnly) return null; | 1864 if (nativeCheckOnly) return null; |
| 1703 return typeCast | 1865 return typeCast |
| 1704 ? const SourceString("listTypeCast") | 1866 ? const CheckedModeHelper(const SourceString("listTypeCast")) |
| 1705 : const SourceString('listTypeCheck'); | 1867 : const CheckedModeHelper(const SourceString('listTypeCheck')); |
| 1706 } else { | 1868 } else { |
| 1707 if (Elements.isListSupertype(element, compiler)) { | 1869 if (Elements.isListSupertype(element, compiler)) { |
| 1708 if (nativeCheck) { | 1870 if (nativeCheck) { |
| 1709 return typeCast | 1871 return typeCast |
| 1710 ? const SourceString("listSuperNativeTypeCast") | 1872 ? const PropertyCheckedModeHelper(const SourceString("listSuperNat iveTypeCast")) |
| 1711 : const SourceString('listSuperNativeTypeCheck'); | 1873 : const PropertyCheckedModeHelper(const SourceString('listSuperNat iveTypeCheck')); |
| 1712 } else { | 1874 } else { |
| 1713 return typeCast | 1875 return typeCast |
| 1714 ? const SourceString("listSuperTypeCast") | 1876 ? const PropertyCheckedModeHelper(const SourceString("listSuperTyp eCast")) |
| 1715 : const SourceString('listSuperTypeCheck'); | 1877 : const PropertyCheckedModeHelper(const SourceString('listSuperTyp eCheck')); |
| 1716 } | 1878 } |
| 1717 } else { | 1879 } else { |
| 1718 if (nativeCheck) { | 1880 if (nativeCheck) { |
| 1719 // TODO(karlklose): can we get rid of this branch when we use | 1881 // TODO(karlklose): can we get rid of this branch when we use |
| 1720 // interceptors? | 1882 // interceptors? |
| 1721 return typeCast | 1883 return typeCast |
| 1722 ? const SourceString("interceptedTypeCast") | 1884 ? const PropertyCheckedModeHelper(const SourceString("interceptedT ypeCast")) |
| 1723 : const SourceString('interceptedTypeCheck'); | 1885 : const PropertyCheckedModeHelper(const SourceString('interceptedT ypeCheck')); |
| 1724 } else { | 1886 } else { |
| 1725 if (type.kind == TypeKind.INTERFACE && !type.isRaw) { | 1887 if (type.kind == TypeKind.INTERFACE && !type.isRaw) { |
| 1726 return typeCast | 1888 return typeCast |
| 1727 ? const SourceString('subtypeCast') | 1889 ? const SubtypeCheckedModeHelper(const SourceString('subtypeCast ')) |
| 1728 : const SourceString('assertSubtype'); | 1890 : const SubtypeCheckedModeHelper(const SourceString('assertSubty pe')); |
| 1729 } else if (type.kind == TypeKind.TYPE_VARIABLE) { | 1891 } else if (type.kind == TypeKind.TYPE_VARIABLE) { |
| 1730 return typeCast | 1892 return typeCast |
| 1731 ? const SourceString('subtypeOfRuntimeTypeCast') | 1893 ? const TypeVariableCheckedModeHelper(const SourceString('subtyp eOfRuntimeTypeCast')) |
| 1732 : const SourceString('assertSubtypeOfRuntimeType'); | 1894 : const TypeVariableCheckedModeHelper(const SourceString('assert SubtypeOfRuntimeType')); |
| 1895 } else if (type.kind == TypeKind.FUNCTION) { | |
| 1896 return typeCast | |
| 1897 ? const FunctionTypeCheckedModeHelper(const SourceString('functi onSubtypeCast')) | |
| 1898 : const FunctionTypeCheckedModeHelper(const SourceString('assert FunctionSubtype')); | |
| 1733 } else { | 1899 } else { |
| 1734 return typeCast | 1900 return typeCast |
| 1735 ? const SourceString('propertyTypeCast') | 1901 ? const PropertyCheckedModeHelper(const SourceString('propertyTy peCast')) |
| 1736 : const SourceString('propertyTypeCheck'); | 1902 : const PropertyCheckedModeHelper(const SourceString('propertyTy peCheck')); |
| 1737 } | 1903 } |
| 1738 } | 1904 } |
| 1739 } | 1905 } |
| 1740 } | 1906 } |
| 1741 } | 1907 } |
| 1742 | 1908 |
| 1743 void dumpInferredTypes() { | 1909 void dumpInferredTypes() { |
| 1744 print("Inferred argument types:"); | 1910 print("Inferred argument types:"); |
| 1745 print("------------------------"); | 1911 print("------------------------"); |
| 1746 argumentTypes.dump(); | 1912 argumentTypes.dump(); |
| 1747 print(""); | 1913 print(""); |
| 1748 print("Inferred return types:"); | 1914 print("Inferred return types:"); |
| 1749 print("----------------------"); | 1915 print("----------------------"); |
| 1750 dumpReturnTypes(); | 1916 dumpReturnTypes(); |
| 1751 print(""); | 1917 print(""); |
| 1752 print("Inferred field types:"); | 1918 print("Inferred field types:"); |
| 1753 print("------------------------"); | 1919 print("------------------------"); |
| 1754 fieldTypes.dump(); | 1920 fieldTypes.dump(); |
| 1755 print(""); | 1921 print(""); |
| 1756 } | 1922 } |
| 1757 | 1923 |
| 1758 Element getExceptionUnwrapper() { | 1924 Element getExceptionUnwrapper() { |
| 1759 return compiler.findHelper(const SourceString('unwrapException')); | 1925 return compiler.findHelper(const SourceString('unwrapException')); |
| 1760 } | 1926 } |
| 1761 | 1927 |
| 1762 Element getThrowRuntimeError() { | 1928 Element getThrowRuntimeError() { |
| 1763 return compiler.findHelper(const SourceString('throwRuntimeError')); | 1929 return compiler.findHelper(const SourceString('throwRuntimeError')); |
| 1764 } | 1930 } |
| 1765 | 1931 |
| 1932 Element getMalformedTypeCheck() { | |
| 1933 return compiler.findHelper(const SourceString('malformedTypeCheck')); | |
| 1934 } | |
| 1935 | |
| 1766 Element getThrowMalformedSubtypeError() { | 1936 Element getThrowMalformedSubtypeError() { |
| 1767 return compiler.findHelper( | 1937 return compiler.findHelper( |
| 1768 const SourceString('throwMalformedSubtypeError')); | 1938 const SourceString('throwMalformedSubtypeError')); |
| 1769 } | 1939 } |
| 1770 | 1940 |
| 1771 Element getThrowAbstractClassInstantiationError() { | 1941 Element getThrowAbstractClassInstantiationError() { |
| 1772 return compiler.findHelper( | 1942 return compiler.findHelper( |
| 1773 const SourceString('throwAbstractClassInstantiationError')); | 1943 const SourceString('throwAbstractClassInstantiationError')); |
| 1774 } | 1944 } |
| 1775 | 1945 |
| (...skipping 22 matching lines...) Expand all Loading... | |
| 1798 } | 1968 } |
| 1799 | 1969 |
| 1800 Element getSetRuntimeTypeInfo() { | 1970 Element getSetRuntimeTypeInfo() { |
| 1801 return compiler.findHelper(const SourceString('setRuntimeTypeInfo')); | 1971 return compiler.findHelper(const SourceString('setRuntimeTypeInfo')); |
| 1802 } | 1972 } |
| 1803 | 1973 |
| 1804 Element getGetRuntimeTypeInfo() { | 1974 Element getGetRuntimeTypeInfo() { |
| 1805 return compiler.findHelper(const SourceString('getRuntimeTypeInfo')); | 1975 return compiler.findHelper(const SourceString('getRuntimeTypeInfo')); |
| 1806 } | 1976 } |
| 1807 | 1977 |
| 1978 Element getApplySignature() { | |
| 1979 return compiler.findHelper(const SourceString('applySignature')); | |
| 1980 } | |
| 1981 | |
| 1982 Element getGetRuntimeTypeArguments() { | |
| 1983 return compiler.findHelper(const SourceString('getRuntimeTypeArguments')); | |
| 1984 } | |
| 1985 | |
| 1808 Element getGetRuntimeTypeArgument() { | 1986 Element getGetRuntimeTypeArgument() { |
| 1809 return compiler.findHelper(const SourceString('getRuntimeTypeArgument')); | 1987 return compiler.findHelper(const SourceString('getRuntimeTypeArgument')); |
| 1810 } | 1988 } |
| 1811 | 1989 |
| 1812 Element getRuntimeTypeToString() { | 1990 Element getRuntimeTypeToString() { |
| 1813 return compiler.findHelper(const SourceString('runtimeTypeToString')); | 1991 return compiler.findHelper(const SourceString('runtimeTypeToString')); |
| 1814 } | 1992 } |
| 1815 | 1993 |
| 1816 Element getCheckSubtype() { | 1994 Element getCheckSubtype() { |
| 1817 return compiler.findHelper(const SourceString('checkSubtype')); | 1995 return compiler.findHelper(const SourceString('checkSubtype')); |
| 1818 } | 1996 } |
| 1819 | 1997 |
| 1820 Element getAssertSubtype() { | 1998 Element getAssertSubtype() { |
| 1821 return compiler.findHelper(const SourceString('assertSubtype')); | 1999 return compiler.findHelper(const SourceString('assertSubtype')); |
| 1822 } | 2000 } |
| 1823 | 2001 |
| 1824 Element getCheckSubtypeOfRuntimeType() { | 2002 Element getCheckSubtypeOfRuntimeType() { |
| 1825 return compiler.findHelper(const SourceString('checkSubtypeOfRuntimeType')); | 2003 return compiler.findHelper(const SourceString('checkSubtypeOfRuntimeType')); |
| 1826 } | 2004 } |
| 1827 | 2005 |
| 1828 Element getAssertSubtypeOfRuntimeType() { | 2006 Element getAssertSubtypeOfRuntimeType() { |
| 1829 return compiler.findHelper( | 2007 return compiler.findHelper( |
| 1830 const SourceString('assertSubtypeOfRuntimeType')); | 2008 const SourceString('assertSubtypeOfRuntimeType')); |
| 1831 } | 2009 } |
| 1832 | 2010 |
| 2011 Element getCheckFunctionSubtype() { | |
| 2012 return compiler.findHelper(const SourceString('checkFunctionSubtype')); | |
| 2013 } | |
| 2014 | |
| 1833 Element getThrowNoSuchMethod() { | 2015 Element getThrowNoSuchMethod() { |
| 1834 return compiler.findHelper(const SourceString('throwNoSuchMethod')); | 2016 return compiler.findHelper(const SourceString('throwNoSuchMethod')); |
| 1835 } | 2017 } |
| 1836 | 2018 |
| 1837 Element getCreateRuntimeType() { | 2019 Element getCreateRuntimeType() { |
| 1838 return compiler.findHelper(const SourceString('createRuntimeType')); | 2020 return compiler.findHelper(const SourceString('createRuntimeType')); |
| 1839 } | 2021 } |
| 1840 | 2022 |
| 1841 Element getFallThroughError() { | 2023 Element getFallThroughError() { |
| 1842 return compiler.findHelper(const SourceString("getFallThroughError")); | 2024 return compiler.findHelper(const SourceString("getFallThroughError")); |
| (...skipping 31 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 1874 ClassElement get listImplementation => jsArrayClass; | 2056 ClassElement get listImplementation => jsArrayClass; |
| 1875 ClassElement get constListImplementation => jsArrayClass; | 2057 ClassElement get constListImplementation => jsArrayClass; |
| 1876 ClassElement get fixedListImplementation => jsFixedArrayClass; | 2058 ClassElement get fixedListImplementation => jsFixedArrayClass; |
| 1877 ClassElement get growableListImplementation => jsExtendableArrayClass; | 2059 ClassElement get growableListImplementation => jsExtendableArrayClass; |
| 1878 ClassElement get mapImplementation => mapLiteralClass; | 2060 ClassElement get mapImplementation => mapLiteralClass; |
| 1879 ClassElement get constMapImplementation => constMapLiteralClass; | 2061 ClassElement get constMapImplementation => constMapLiteralClass; |
| 1880 ClassElement get typeImplementation => typeLiteralClass; | 2062 ClassElement get typeImplementation => typeLiteralClass; |
| 1881 ClassElement get boolImplementation => jsBoolClass; | 2063 ClassElement get boolImplementation => jsBoolClass; |
| 1882 ClassElement get nullImplementation => jsNullClass; | 2064 ClassElement get nullImplementation => jsNullClass; |
| 1883 } | 2065 } |
| OLD | NEW |