Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(937)

Side by Side Diff: pkg/compiler/lib/src/ssa/builder.dart

Issue 2814453005: Merge CommonElements and BackendHelpers! (Closed)
Patch Set: comments and re-merge, take two Created 3 years, 8 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
« no previous file with comments | « pkg/compiler/lib/src/patch_parser.dart ('k') | pkg/compiler/lib/src/ssa/builder_kernel.dart » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
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 'dart:collection'; 5 import 'dart:collection';
6 6
7 import 'package:js_runtime/shared/embedded_names.dart'; 7 import 'package:js_runtime/shared/embedded_names.dart';
8 8
9 import '../closure.dart'; 9 import '../closure.dart';
10 import '../common.dart'; 10 import '../common.dart';
11 import '../common/codegen.dart' show CodegenRegistry, CodegenWorkItem; 11 import '../common/codegen.dart' show CodegenRegistry, CodegenWorkItem;
12 import '../common/names.dart' show Identifiers, Selectors; 12 import '../common/names.dart' show Identifiers, Selectors;
13 import '../common/tasks.dart' show CompilerTask; 13 import '../common/tasks.dart' show CompilerTask;
14 import '../constants/constant_system.dart'; 14 import '../constants/constant_system.dart';
15 import '../constants/expressions.dart'; 15 import '../constants/expressions.dart';
16 import '../constants/values.dart'; 16 import '../constants/values.dart';
17 import '../elements/resolution_types.dart'; 17 import '../elements/resolution_types.dart';
18 import '../elements/types.dart'; 18 import '../elements/types.dart';
19 import '../diagnostics/messages.dart' show Message, MessageTemplate; 19 import '../diagnostics/messages.dart' show Message, MessageTemplate;
20 import '../dump_info.dart' show InfoReporter; 20 import '../dump_info.dart' show InfoReporter;
21 import '../elements/elements.dart'; 21 import '../elements/elements.dart';
22 import '../elements/entities.dart'; 22 import '../elements/entities.dart';
23 import '../elements/modelx.dart' show ConstructorBodyElementX; 23 import '../elements/modelx.dart' show ConstructorBodyElementX;
24 import '../io/source_information.dart'; 24 import '../io/source_information.dart';
25 import '../js/js.dart' as js; 25 import '../js/js.dart' as js;
26 import '../js_backend/backend_helpers.dart' show BackendHelpers; 26 import '../js_backend/backend.dart' show JavaScriptBackend;
27 import '../js_backend/js_backend.dart'; 27 import '../js_backend/js_backend.dart';
28 import '../js_emitter/js_emitter.dart' show CodeEmitterTask, NativeEmitter; 28 import '../js_emitter/js_emitter.dart' show CodeEmitterTask, NativeEmitter;
29 import '../native/native.dart' as native; 29 import '../native/native.dart' as native;
30 import '../resolution/operators.dart'; 30 import '../resolution/operators.dart';
31 import '../resolution/semantic_visitor.dart'; 31 import '../resolution/semantic_visitor.dart';
32 import '../resolution/tree_elements.dart' show TreeElements; 32 import '../resolution/tree_elements.dart' show TreeElements;
33 import '../tree/tree.dart' as ast; 33 import '../tree/tree.dart' as ast;
34 import '../types/types.dart'; 34 import '../types/types.dart';
35 import '../universe/call_structure.dart' show CallStructure; 35 import '../universe/call_structure.dart' show CallStructure;
36 import '../universe/selector.dart' show Selector; 36 import '../universe/selector.dart' show Selector;
(...skipping 663 matching lines...) Expand 10 before | Expand all | Expand 10 after
700 }, 700 },
701 visitElse: null, 701 visitElse: null,
702 sourceInformation: sourceInformationBuilder.buildIf(function.body)); 702 sourceInformation: sourceInformationBuilder.buildIf(function.body));
703 } 703 }
704 } 704 }
705 if (const bool.fromEnvironment('unreachable-throw')) { 705 if (const bool.fromEnvironment('unreachable-throw')) {
706 var emptyParameters = 706 var emptyParameters =
707 parameters.values.where((p) => p.instructionType.isEmpty); 707 parameters.values.where((p) => p.instructionType.isEmpty);
708 if (emptyParameters.length > 0) { 708 if (emptyParameters.length > 0) {
709 addComment('${emptyParameters} inferred as [empty]'); 709 addComment('${emptyParameters} inferred as [empty]');
710 pushInvokeStatic(function.body, helpers.assertUnreachableMethod, []); 710 pushInvokeStatic(
711 function.body, commonElements.assertUnreachableMethod, []);
711 pop(); 712 pop();
712 return closeFunction(); 713 return closeFunction();
713 } 714 }
714 } 715 }
715 function.body.accept(this); 716 function.body.accept(this);
716 return closeFunction(); 717 return closeFunction();
717 } 718 }
718 719
719 /// Adds a JavaScript comment to the output. The comment will be omitted in 720 /// Adds a JavaScript comment to the output. The comment will be omitted in
720 /// minified mode. Each line in [text] is preceded with `//` and indented. 721 /// minified mode. Each line in [text] is preceded with `//` and indented.
(...skipping 706 matching lines...) Expand 10 before | Expand all | Expand 10 after
1427 // Otherwise it is a lazy initializer which does not have parameters. 1428 // Otherwise it is a lazy initializer which does not have parameters.
1428 assert(element is VariableElement); 1429 assert(element is VariableElement);
1429 } 1430 }
1430 1431
1431 insertTraceCall(element); 1432 insertTraceCall(element);
1432 insertCoverageCall(element); 1433 insertCoverageCall(element);
1433 } 1434 }
1434 1435
1435 insertTraceCall(Element element) { 1436 insertTraceCall(Element element) {
1436 if (JavaScriptBackend.TRACE_METHOD == 'console') { 1437 if (JavaScriptBackend.TRACE_METHOD == 'console') {
1437 if (element == helpers.traceHelper) return; 1438 if (element == commonElements.traceHelper) return;
1438 n(e) => e == null ? '' : e.name; 1439 n(e) => e == null ? '' : e.name;
1439 String name = "${n(element.library)}:${n(element.enclosingClass)}." 1440 String name = "${n(element.library)}:${n(element.enclosingClass)}."
1440 "${n(element)}"; 1441 "${n(element)}";
1441 HConstant nameConstant = addConstantString(name); 1442 HConstant nameConstant = addConstantString(name);
1442 add(new HInvokeStatic(helpers.traceHelper, <HInstruction>[nameConstant], 1443 add(new HInvokeStatic(commonElements.traceHelper,
1443 commonMasks.dynamicType)); 1444 <HInstruction>[nameConstant], commonMasks.dynamicType));
1444 } 1445 }
1445 } 1446 }
1446 1447
1447 insertCoverageCall(Element element) { 1448 insertCoverageCall(Element element) {
1448 if (JavaScriptBackend.TRACE_METHOD == 'post') { 1449 if (JavaScriptBackend.TRACE_METHOD == 'post') {
1449 if (element == helpers.traceHelper) return; 1450 if (element == commonElements.traceHelper) return;
1450 // TODO(sigmund): create a better uuid for elements. 1451 // TODO(sigmund): create a better uuid for elements.
1451 HConstant idConstant = 1452 HConstant idConstant =
1452 graph.addConstantInt(element.hashCode, closedWorld); 1453 graph.addConstantInt(element.hashCode, closedWorld);
1453 HConstant nameConstant = addConstantString(element.name); 1454 HConstant nameConstant = addConstantString(element.name);
1454 add(new HInvokeStatic(helpers.traceHelper, 1455 add(new HInvokeStatic(commonElements.traceHelper,
1455 <HInstruction>[idConstant, nameConstant], commonMasks.dynamicType)); 1456 <HInstruction>[idConstant, nameConstant], commonMasks.dynamicType));
1456 } 1457 }
1457 } 1458 }
1458 1459
1459 void assertIsSubtype(ast.Node node, ResolutionDartType subtype, 1460 void assertIsSubtype(ast.Node node, ResolutionDartType subtype,
1460 ResolutionDartType supertype, String message) { 1461 ResolutionDartType supertype, String message) {
1461 HInstruction subtypeInstruction = typeBuilder.analyzeTypeArgument( 1462 HInstruction subtypeInstruction = typeBuilder.analyzeTypeArgument(
1462 localsHandler.substInContext(subtype), sourceElement); 1463 localsHandler.substInContext(subtype), sourceElement);
1463 HInstruction supertypeInstruction = typeBuilder.analyzeTypeArgument( 1464 HInstruction supertypeInstruction = typeBuilder.analyzeTypeArgument(
1464 localsHandler.substInContext(supertype), sourceElement); 1465 localsHandler.substInContext(supertype), sourceElement);
1465 HInstruction messageInstruction = graph.addConstantString( 1466 HInstruction messageInstruction = graph.addConstantString(
1466 new ast.DartString.literal(message), closedWorld); 1467 new ast.DartString.literal(message), closedWorld);
1467 MethodElement element = helpers.assertIsSubtype; 1468 MethodElement element = commonElements.assertIsSubtype;
1468 var inputs = <HInstruction>[ 1469 var inputs = <HInstruction>[
1469 subtypeInstruction, 1470 subtypeInstruction,
1470 supertypeInstruction, 1471 supertypeInstruction,
1471 messageInstruction 1472 messageInstruction
1472 ]; 1473 ];
1473 HInstruction assertIsSubtype = 1474 HInstruction assertIsSubtype =
1474 new HInvokeStatic(element, inputs, subtypeInstruction.instructionType); 1475 new HInvokeStatic(element, inputs, subtypeInstruction.instructionType);
1475 registry?.registerTypeVariableBoundsSubtypeCheck(subtype, supertype); 1476 registry?.registerTypeVariableBoundsSubtypeCheck(subtype, supertype);
1476 add(assertIsSubtype); 1477 add(assertIsSubtype);
1477 } 1478 }
(...skipping 44 matching lines...) Expand 10 before | Expand all | Expand 10 after
1522 1523
1523 visitAssert(ast.Assert node) { 1524 visitAssert(ast.Assert node) {
1524 if (!options.enableUserAssertions) return; 1525 if (!options.enableUserAssertions) return;
1525 1526
1526 if (!node.hasMessage) { 1527 if (!node.hasMessage) {
1527 // Generate: 1528 // Generate:
1528 // 1529 //
1529 // assertHelper(condition); 1530 // assertHelper(condition);
1530 // 1531 //
1531 visit(node.condition); 1532 visit(node.condition);
1532 pushInvokeStatic(node, helpers.assertHelper, [pop()]); 1533 pushInvokeStatic(node, commonElements.assertHelper, [pop()]);
1533 pop(); 1534 pop();
1534 return; 1535 return;
1535 } 1536 }
1536 // Assert has message. Generate: 1537 // Assert has message. Generate:
1537 // 1538 //
1538 // if (assertTest(condition)) assertThrow(message); 1539 // if (assertTest(condition)) assertThrow(message);
1539 // 1540 //
1540 void buildCondition() { 1541 void buildCondition() {
1541 visit(node.condition); 1542 visit(node.condition);
1542 pushInvokeStatic(node, helpers.assertTest, [pop()]); 1543 pushInvokeStatic(node, commonElements.assertTest, [pop()]);
1543 } 1544 }
1544 1545
1545 void fail() { 1546 void fail() {
1546 visit(node.message); 1547 visit(node.message);
1547 pushInvokeStatic(node, helpers.assertThrow, [pop()]); 1548 pushInvokeStatic(node, commonElements.assertThrow, [pop()]);
1548 pop(); 1549 pop();
1549 } 1550 }
1550 1551
1551 handleIf(node: node, visitCondition: buildCondition, visitThen: fail); 1552 handleIf(node: node, visitCondition: buildCondition, visitThen: fail);
1552 } 1553 }
1553 1554
1554 visitBlock(ast.Block node) { 1555 visitBlock(ast.Block node) {
1555 assert(!isAborted()); 1556 assert(!isAborted());
1556 if (!isReachable) return; // This can only happen when inlining. 1557 if (!isReachable) return; // This can only happen when inlining.
1557 for (Link<ast.Node> link = node.statements.nodes; 1558 for (Link<ast.Node> link = node.statements.nodes;
(...skipping 462 matching lines...) Expand 10 before | Expand all | Expand 10 after
2020 /// Inserts a call to checkDeferredIsLoaded for [prefixElement]. 2021 /// Inserts a call to checkDeferredIsLoaded for [prefixElement].
2021 /// If [prefixElement] is [null] ndo nothing. 2022 /// If [prefixElement] is [null] ndo nothing.
2022 void generateIsDeferredLoadedCheckIfNeeded( 2023 void generateIsDeferredLoadedCheckIfNeeded(
2023 PrefixElement prefixElement, ast.Node location) { 2024 PrefixElement prefixElement, ast.Node location) {
2024 if (prefixElement == null) return; 2025 if (prefixElement == null) return;
2025 String loadId = 2026 String loadId =
2026 compiler.deferredLoadTask.getImportDeferName(location, prefixElement); 2027 compiler.deferredLoadTask.getImportDeferName(location, prefixElement);
2027 HInstruction loadIdConstant = addConstantString(loadId); 2028 HInstruction loadIdConstant = addConstantString(loadId);
2028 String uri = prefixElement.deferredImport.uri.toString(); 2029 String uri = prefixElement.deferredImport.uri.toString();
2029 HInstruction uriConstant = addConstantString(uri); 2030 HInstruction uriConstant = addConstantString(uri);
2030 MethodElement helper = helpers.checkDeferredIsLoaded; 2031 MethodElement helper = commonElements.checkDeferredIsLoaded;
2031 pushInvokeStatic(location, helper, [loadIdConstant, uriConstant]); 2032 pushInvokeStatic(location, helper, [loadIdConstant, uriConstant]);
2032 pop(); 2033 pop();
2033 } 2034 }
2034 2035
2035 /// Inserts a call to checkDeferredIsLoaded if the send has a prefix that 2036 /// Inserts a call to checkDeferredIsLoaded if the send has a prefix that
2036 /// resolves to a deferred library. 2037 /// resolves to a deferred library.
2037 void generateIsDeferredLoadedCheckOfSend(ast.Send node) { 2038 void generateIsDeferredLoadedCheckOfSend(ast.Send node) {
2038 generateIsDeferredLoadedCheckIfNeeded( 2039 generateIsDeferredLoadedCheckIfNeeded(
2039 compiler.deferredLoadTask.deferredPrefixElement(node, elements), node); 2040 compiler.deferredLoadTask.deferredPrefixElement(node, elements), node);
2040 } 2041 }
(...skipping 345 matching lines...) Expand 10 before | Expand all | Expand 10 after
2386 generateTypeError(node, message); 2387 generateTypeError(node, message);
2387 HInstruction call = pop(); 2388 HInstruction call = pop();
2388 return new HIs.compound(type, expression, call, commonMasks.boolType); 2389 return new HIs.compound(type, expression, call, commonMasks.boolType);
2389 } else if (type.isFunctionType) { 2390 } else if (type.isFunctionType) {
2390 HInstruction representation = 2391 HInstruction representation =
2391 typeBuilder.analyzeTypeArgument(type, sourceElement); 2392 typeBuilder.analyzeTypeArgument(type, sourceElement);
2392 List<HInstruction> inputs = <HInstruction>[ 2393 List<HInstruction> inputs = <HInstruction>[
2393 expression, 2394 expression,
2394 representation, 2395 representation,
2395 ]; 2396 ];
2396 pushInvokeStatic(node, helpers.functionTypeTest, inputs, 2397 pushInvokeStatic(node, commonElements.functionTypeTest, inputs,
2397 typeMask: commonMasks.boolType); 2398 typeMask: commonMasks.boolType);
2398 HInstruction call = pop(); 2399 HInstruction call = pop();
2399 return new HIs.compound(type, expression, call, commonMasks.boolType); 2400 return new HIs.compound(type, expression, call, commonMasks.boolType);
2400 } else if (type.isTypeVariable) { 2401 } else if (type.isTypeVariable) {
2401 HInstruction runtimeType = 2402 HInstruction runtimeType =
2402 typeBuilder.addTypeVariableReference(type, sourceElement); 2403 typeBuilder.addTypeVariableReference(type, sourceElement);
2403 MethodElement helper = helpers.checkSubtypeOfRuntimeType; 2404 MethodElement helper = commonElements.checkSubtypeOfRuntimeType;
2404 List<HInstruction> inputs = <HInstruction>[expression, runtimeType]; 2405 List<HInstruction> inputs = <HInstruction>[expression, runtimeType];
2405 pushInvokeStatic(null, helper, inputs, typeMask: commonMasks.boolType); 2406 pushInvokeStatic(null, helper, inputs, typeMask: commonMasks.boolType);
2406 HInstruction call = pop(); 2407 HInstruction call = pop();
2407 return new HIs.variable(type, expression, call, commonMasks.boolType); 2408 return new HIs.variable(type, expression, call, commonMasks.boolType);
2408 } else if (RuntimeTypesSubstitutions.hasTypeArguments(type)) { 2409 } else if (RuntimeTypesSubstitutions.hasTypeArguments(type)) {
2409 ClassElement element = type.element; 2410 ClassElement element = type.element;
2410 MethodElement helper = helpers.checkSubtype; 2411 MethodElement helper = commonElements.checkSubtype;
2411 HInstruction representations = 2412 HInstruction representations =
2412 typeBuilder.buildTypeArgumentRepresentations(type, sourceElement); 2413 typeBuilder.buildTypeArgumentRepresentations(type, sourceElement);
2413 add(representations); 2414 add(representations);
2414 js.Name operator = namer.operatorIs(element); 2415 js.Name operator = namer.operatorIs(element);
2415 HInstruction isFieldName = addConstantStringFromName(operator); 2416 HInstruction isFieldName = addConstantStringFromName(operator);
2416 HInstruction asFieldName = closedWorld.hasAnyStrictSubtype(element) 2417 HInstruction asFieldName = closedWorld.hasAnyStrictSubtype(element)
2417 ? addConstantStringFromName(namer.substitutionName(element)) 2418 ? addConstantStringFromName(namer.substitutionName(element))
2418 : graph.addConstantNull(closedWorld); 2419 : graph.addConstantNull(closedWorld);
2419 List<HInstruction> inputs = <HInstruction>[ 2420 List<HInstruction> inputs = <HInstruction>[
2420 expression, 2421 expression,
(...skipping 243 matching lines...) Expand 10 before | Expand all | Expand 10 after
2664 // If the isolate library is not used, we just generate code 2665 // If the isolate library is not used, we just generate code
2665 // to fetch the static state. 2666 // to fetch the static state.
2666 String name = namer.staticStateHolder; 2667 String name = namer.staticStateHolder;
2667 push(new HForeignCode( 2668 push(new HForeignCode(
2668 js.js.parseForeignJS(name), commonMasks.dynamicType, <HInstruction>[], 2669 js.js.parseForeignJS(name), commonMasks.dynamicType, <HInstruction>[],
2669 nativeBehavior: native.NativeBehavior.DEPENDS_OTHER)); 2670 nativeBehavior: native.NativeBehavior.DEPENDS_OTHER));
2670 } else { 2671 } else {
2671 // Call a helper method from the isolate library. The isolate 2672 // Call a helper method from the isolate library. The isolate
2672 // library uses its own isolate structure, that encapsulates 2673 // library uses its own isolate structure, that encapsulates
2673 // Leg's isolate. 2674 // Leg's isolate.
2674 MethodElement element = helpers.currentIsolate; 2675 MethodElement element = commonElements.currentIsolate;
2675 if (element == null) { 2676 if (element == null) {
2676 reporter.internalError(node, 'Isolate library and compiler mismatch.'); 2677 reporter.internalError(node, 'Isolate library and compiler mismatch.');
2677 } 2678 }
2678 pushInvokeStatic(null, element, [], typeMask: commonMasks.dynamicType); 2679 pushInvokeStatic(null, element, [], typeMask: commonMasks.dynamicType);
2679 } 2680 }
2680 } 2681 }
2681 2682
2682 void handleForeignJsGetFlag(ast.Send node) { 2683 void handleForeignJsGetFlag(ast.Send node) {
2683 List<ast.Node> arguments = node.arguments.toList(); 2684 List<ast.Node> arguments = node.arguments.toList();
2684 ast.Node argument; 2685 ast.Node argument;
(...skipping 47 matching lines...) Expand 10 before | Expand all | Expand 10 after
2732 default: 2733 default:
2733 for (int i = 1; i < arguments.length; i++) { 2734 for (int i = 1; i < arguments.length; i++) {
2734 reporter.reportErrorMessage(arguments[i], MessageKind.GENERIC, 2735 reporter.reportErrorMessage(arguments[i], MessageKind.GENERIC,
2735 {'text': 'Error: Extra argument to JS_GET_NAME.'}); 2736 {'text': 'Error: Extra argument to JS_GET_NAME.'});
2736 } 2737 }
2737 return; 2738 return;
2738 } 2739 }
2739 Element element = elements[argument]; 2740 Element element = elements[argument];
2740 if (element == null || 2741 if (element == null ||
2741 element is! EnumConstantElement || 2742 element is! EnumConstantElement ||
2742 element.enclosingClass != helpers.jsGetNameEnum) { 2743 element.enclosingClass != commonElements.jsGetNameEnum) {
2743 reporter.reportErrorMessage(argument, MessageKind.GENERIC, 2744 reporter.reportErrorMessage(argument, MessageKind.GENERIC,
2744 {'text': 'Error: Expected a JsGetName enum value.'}); 2745 {'text': 'Error: Expected a JsGetName enum value.'});
2745 } 2746 }
2746 EnumConstantElement enumConstant = element; 2747 EnumConstantElement enumConstant = element;
2747 int index = enumConstant.index; 2748 int index = enumConstant.index;
2748 stack.add(addConstantStringFromName( 2749 stack.add(addConstantStringFromName(
2749 namer.getNameForJsGetName(argument, JsGetName.values[index]))); 2750 namer.getNameForJsGetName(argument, JsGetName.values[index])));
2750 } 2751 }
2751 2752
2752 void handleForeignJsBuiltin(ast.Send node) { 2753 void handleForeignJsBuiltin(ast.Send node) {
2753 List<ast.Node> arguments = node.arguments.toList(); 2754 List<ast.Node> arguments = node.arguments.toList();
2754 ast.Node argument; 2755 ast.Node argument;
2755 if (arguments.length < 2) { 2756 if (arguments.length < 2) {
2756 reporter.reportErrorMessage(node, MessageKind.GENERIC, 2757 reporter.reportErrorMessage(node, MessageKind.GENERIC,
2757 {'text': 'Error: Expected at least two arguments to JS_BUILTIN.'}); 2758 {'text': 'Error: Expected at least two arguments to JS_BUILTIN.'});
2758 } 2759 }
2759 2760
2760 Element builtinElement = elements[arguments[1]]; 2761 Element builtinElement = elements[arguments[1]];
2761 if (builtinElement == null || 2762 if (builtinElement == null ||
2762 (builtinElement is! EnumConstantElement) || 2763 (builtinElement is! EnumConstantElement) ||
2763 builtinElement.enclosingClass != helpers.jsBuiltinEnum) { 2764 builtinElement.enclosingClass != commonElements.jsBuiltinEnum) {
2764 reporter.reportErrorMessage(argument, MessageKind.GENERIC, 2765 reporter.reportErrorMessage(argument, MessageKind.GENERIC,
2765 {'text': 'Error: Expected a JsBuiltin enum value.'}); 2766 {'text': 'Error: Expected a JsBuiltin enum value.'});
2766 } 2767 }
2767 EnumConstantElement enumConstant = builtinElement; 2768 EnumConstantElement enumConstant = builtinElement;
2768 int index = enumConstant.index; 2769 int index = enumConstant.index;
2769 2770
2770 js.Template template = emitter.builtinTemplateFor(JsBuiltin.values[index]); 2771 js.Template template = emitter.builtinTemplateFor(JsBuiltin.values[index]);
2771 2772
2772 List<HInstruction> compiledArguments = <HInstruction>[]; 2773 List<HInstruction> compiledArguments = <HInstruction>[];
2773 for (int i = 2; i < arguments.length; i++) { 2774 for (int i = 2; i < arguments.length; i++) {
(...skipping 83 matching lines...) Expand 10 before | Expand all | Expand 10 after
2857 void handleForeignJsCallInIsolate(ast.Send node) { 2858 void handleForeignJsCallInIsolate(ast.Send node) {
2858 Link<ast.Node> link = node.arguments; 2859 Link<ast.Node> link = node.arguments;
2859 if (!backendUsage.isIsolateInUse) { 2860 if (!backendUsage.isIsolateInUse) {
2860 // If the isolate library is not used, we just invoke the 2861 // If the isolate library is not used, we just invoke the
2861 // closure. 2862 // closure.
2862 visit(link.tail.head); 2863 visit(link.tail.head);
2863 push(new HInvokeClosure(new Selector.callClosure(0), 2864 push(new HInvokeClosure(new Selector.callClosure(0),
2864 <HInstruction>[pop()], commonMasks.dynamicType)); 2865 <HInstruction>[pop()], commonMasks.dynamicType));
2865 } else { 2866 } else {
2866 // Call a helper method from the isolate library. 2867 // Call a helper method from the isolate library.
2867 MethodElement element = helpers.callInIsolate; 2868 MethodElement element = commonElements.callInIsolate;
2868 if (element == null) { 2869 if (element == null) {
2869 reporter.internalError(node, 'Isolate library and compiler mismatch.'); 2870 reporter.internalError(node, 'Isolate library and compiler mismatch.');
2870 } 2871 }
2871 List<HInstruction> inputs = <HInstruction>[]; 2872 List<HInstruction> inputs = <HInstruction>[];
2872 addGenericSendArgumentsToList(link, inputs); 2873 addGenericSendArgumentsToList(link, inputs);
2873 pushInvokeStatic(node, element, inputs, 2874 pushInvokeStatic(node, element, inputs,
2874 typeMask: commonMasks.dynamicType); 2875 typeMask: commonMasks.dynamicType);
2875 } 2876 }
2876 } 2877 }
2877 2878
(...skipping 55 matching lines...) Expand 10 before | Expand all | Expand 10 after
2933 if (!node.arguments.isEmpty) { 2934 if (!node.arguments.isEmpty) {
2934 reporter.internalError(node.argumentsNode, 'Too many arguments.'); 2935 reporter.internalError(node.argumentsNode, 'Too many arguments.');
2935 } 2936 }
2936 push(new HForeignCode(js.js.parseForeignJS(namer.staticStateHolder), 2937 push(new HForeignCode(js.js.parseForeignJS(namer.staticStateHolder),
2937 commonMasks.dynamicType, <HInstruction>[], 2938 commonMasks.dynamicType, <HInstruction>[],
2938 nativeBehavior: native.NativeBehavior.DEPENDS_OTHER)); 2939 nativeBehavior: native.NativeBehavior.DEPENDS_OTHER));
2939 } 2940 }
2940 2941
2941 void handleForeignSend(ast.Send node, FunctionElement element) { 2942 void handleForeignSend(ast.Send node, FunctionElement element) {
2942 String name = element.name; 2943 String name = element.name;
2943 if (name == BackendHelpers.JS) { 2944 if (name == JavaScriptBackend.JS) {
2944 handleForeignJs(node); 2945 handleForeignJs(node);
2945 } else if (name == 'JS_CURRENT_ISOLATE_CONTEXT') { 2946 } else if (name == 'JS_CURRENT_ISOLATE_CONTEXT') {
2946 handleForeignJsCurrentIsolateContext(node); 2947 handleForeignJsCurrentIsolateContext(node);
2947 } else if (name == 'JS_CALL_IN_ISOLATE') { 2948 } else if (name == 'JS_CALL_IN_ISOLATE') {
2948 handleForeignJsCallInIsolate(node); 2949 handleForeignJsCallInIsolate(node);
2949 } else if (name == 'DART_CLOSURE_TO_JS') { 2950 } else if (name == 'DART_CLOSURE_TO_JS') {
2950 handleForeignDartClosureToJs(node, 'DART_CLOSURE_TO_JS'); 2951 handleForeignDartClosureToJs(node, 'DART_CLOSURE_TO_JS');
2951 } else if (name == 'RAW_DART_FUNCTION_REF') { 2952 } else if (name == 'RAW_DART_FUNCTION_REF') {
2952 handleForeignRawFunctionRef(node, 'RAW_DART_FUNCTION_REF'); 2953 handleForeignRawFunctionRef(node, 'RAW_DART_FUNCTION_REF');
2953 } else if (name == 'JS_SET_STATIC_STATE') { 2954 } else if (name == 'JS_SET_STATIC_STATE') {
2954 handleForeignJsSetStaticState(node); 2955 handleForeignJsSetStaticState(node);
2955 } else if (name == 'JS_GET_STATIC_STATE') { 2956 } else if (name == 'JS_GET_STATIC_STATE') {
2956 handleForeignJsGetStaticState(node); 2957 handleForeignJsGetStaticState(node);
2957 } else if (name == 'JS_GET_NAME') { 2958 } else if (name == 'JS_GET_NAME') {
2958 handleForeignJsGetName(node); 2959 handleForeignJsGetName(node);
2959 } else if (name == BackendHelpers.JS_EMBEDDED_GLOBAL) { 2960 } else if (name == JavaScriptBackend.JS_EMBEDDED_GLOBAL) {
2960 handleForeignJsEmbeddedGlobal(node); 2961 handleForeignJsEmbeddedGlobal(node);
2961 } else if (name == BackendHelpers.JS_BUILTIN) { 2962 } else if (name == JavaScriptBackend.JS_BUILTIN) {
2962 handleForeignJsBuiltin(node); 2963 handleForeignJsBuiltin(node);
2963 } else if (name == 'JS_GET_FLAG') { 2964 } else if (name == 'JS_GET_FLAG') {
2964 handleForeignJsGetFlag(node); 2965 handleForeignJsGetFlag(node);
2965 } else if (name == 'JS_EFFECT') { 2966 } else if (name == 'JS_EFFECT') {
2966 stack.add(graph.addConstantNull(closedWorld)); 2967 stack.add(graph.addConstantNull(closedWorld));
2967 } else if (name == BackendHelpers.JS_INTERCEPTOR_CONSTANT) { 2968 } else if (name == JavaScriptBackend.JS_INTERCEPTOR_CONSTANT) {
2968 handleJsInterceptorConstant(node); 2969 handleJsInterceptorConstant(node);
2969 } else if (name == 'JS_STRING_CONCAT') { 2970 } else if (name == 'JS_STRING_CONCAT') {
2970 handleJsStringConcat(node); 2971 handleJsStringConcat(node);
2971 } else { 2972 } else {
2972 reporter.internalError(node, "Unknown foreign: ${element}"); 2973 reporter.internalError(node, "Unknown foreign: ${element}");
2973 } 2974 }
2974 } 2975 }
2975 2976
2976 generateDeferredLoaderGet(ast.Send node, FunctionElement deferredLoader, 2977 generateDeferredLoaderGet(ast.Send node, FunctionElement deferredLoader,
2977 SourceInformation sourceInformation) { 2978 SourceInformation sourceInformation) {
2978 // Until now we only handle these as getters. 2979 // Until now we only handle these as getters.
2979 invariant(node, deferredLoader.isDeferredLoaderGetter); 2980 invariant(node, deferredLoader.isDeferredLoaderGetter);
2980 FunctionEntity loadFunction = helpers.loadLibraryWrapper; 2981 FunctionEntity loadFunction = commonElements.loadLibraryWrapper;
2981 PrefixElement prefixElement = deferredLoader.enclosingElement; 2982 PrefixElement prefixElement = deferredLoader.enclosingElement;
2982 String loadId = 2983 String loadId =
2983 compiler.deferredLoadTask.getImportDeferName(node, prefixElement); 2984 compiler.deferredLoadTask.getImportDeferName(node, prefixElement);
2984 var inputs = [ 2985 var inputs = [
2985 graph.addConstantString(new ast.DartString.literal(loadId), closedWorld) 2986 graph.addConstantString(new ast.DartString.literal(loadId), closedWorld)
2986 ]; 2987 ];
2987 push(new HInvokeStatic(loadFunction, inputs, commonMasks.nonNullType, 2988 push(new HInvokeStatic(loadFunction, inputs, commonMasks.nonNullType,
2988 targetCanThrow: false) 2989 targetCanThrow: false)
2989 ..sourceInformation = sourceInformation); 2990 ..sourceInformation = sourceInformation);
2990 } 2991 }
(...skipping 17 matching lines...) Expand all
3008 registry?.registerDynamicUse(new DynamicUse(selector, null)); 3009 registry?.registerDynamicUse(new DynamicUse(selector, null));
3009 } 3010 }
3010 String publicName = name; 3011 String publicName = name;
3011 if (selector.isSetter) publicName += '='; 3012 if (selector.isSetter) publicName += '=';
3012 3013
3013 ConstantValue nameConstant = 3014 ConstantValue nameConstant =
3014 constantSystem.createString(new ast.DartString.literal(publicName)); 3015 constantSystem.createString(new ast.DartString.literal(publicName));
3015 3016
3016 js.Name internalName = namer.invocationName(selector); 3017 js.Name internalName = namer.invocationName(selector);
3017 3018
3018 MethodElement createInvocationMirror = helpers.createInvocationMirror; 3019 MethodElement createInvocationMirror =
3020 commonElements.createInvocationMirror;
3019 var argumentsInstruction = buildLiteralList(arguments); 3021 var argumentsInstruction = buildLiteralList(arguments);
3020 add(argumentsInstruction); 3022 add(argumentsInstruction);
3021 3023
3022 var argumentNames = new List<HInstruction>(); 3024 var argumentNames = new List<HInstruction>();
3023 for (String argumentName in selector.namedArguments) { 3025 for (String argumentName in selector.namedArguments) {
3024 ConstantValue argumentNameConstant = 3026 ConstantValue argumentNameConstant =
3025 constantSystem.createString(new ast.DartString.literal(argumentName)); 3027 constantSystem.createString(new ast.DartString.literal(argumentName));
3026 argumentNames.add(graph.addConstant(argumentNameConstant, closedWorld)); 3028 argumentNames.add(graph.addConstant(argumentNameConstant, closedWorld));
3027 } 3029 }
3028 var argumentNamesInstruction = buildLiteralList(argumentNames); 3030 var argumentNamesInstruction = buildLiteralList(argumentNames);
(...skipping 209 matching lines...) Expand 10 before | Expand all | Expand 10 after
3238 inputs.add(typeBuilder.analyzeTypeArgument(argument, sourceElement)); 3240 inputs.add(typeBuilder.analyzeTypeArgument(argument, sourceElement));
3239 }); 3241 });
3240 // TODO(15489): Register at codegen. 3242 // TODO(15489): Register at codegen.
3241 registry?.registerInstantiation(type); 3243 registry?.registerInstantiation(type);
3242 return callSetRuntimeTypeInfoWithTypeArguments(type, inputs, newObject); 3244 return callSetRuntimeTypeInfoWithTypeArguments(type, inputs, newObject);
3243 } 3245 }
3244 3246
3245 HInstruction callSetRuntimeTypeInfo( 3247 HInstruction callSetRuntimeTypeInfo(
3246 HInstruction typeInfo, HInstruction newObject) { 3248 HInstruction typeInfo, HInstruction newObject) {
3247 // Set the runtime type information on the object. 3249 // Set the runtime type information on the object.
3248 MethodElement typeInfoSetterElement = helpers.setRuntimeTypeInfo; 3250 MethodElement typeInfoSetterElement = commonElements.setRuntimeTypeInfo;
3249 pushInvokeStatic( 3251 pushInvokeStatic(
3250 null, typeInfoSetterElement, <HInstruction>[newObject, typeInfo], 3252 null, typeInfoSetterElement, <HInstruction>[newObject, typeInfo],
3251 typeMask: commonMasks.dynamicType, 3253 typeMask: commonMasks.dynamicType,
3252 sourceInformation: newObject.sourceInformation); 3254 sourceInformation: newObject.sourceInformation);
3253 3255
3254 // The new object will now be referenced through the 3256 // The new object will now be referenced through the
3255 // `setRuntimeTypeInfo` call. We therefore set the type of that 3257 // `setRuntimeTypeInfo` call. We therefore set the type of that
3256 // instruction to be of the object's type. 3258 // instruction to be of the object's type.
3257 assert(invariant(CURRENT_ELEMENT_SPANNABLE, 3259 assert(invariant(CURRENT_ELEMENT_SPANNABLE,
3258 stack.last is HInvokeStatic || stack.last == newObject, 3260 stack.last is HInvokeStatic || stack.last == newObject,
(...skipping 53 matching lines...) Expand 10 before | Expand all | Expand 10 after
3312 } 3314 }
3313 } 3315 }
3314 3316
3315 CallStructure callStructure = elements.getSelector(send).callStructure; 3317 CallStructure callStructure = elements.getSelector(send).callStructure;
3316 ConstructorElement constructorDeclaration = constructor; 3318 ConstructorElement constructorDeclaration = constructor;
3317 ConstructorElement constructorImplementation = constructor.implementation; 3319 ConstructorElement constructorImplementation = constructor.implementation;
3318 constructor = constructorImplementation.effectiveTarget; 3320 constructor = constructorImplementation.effectiveTarget;
3319 3321
3320 final bool isSymbolConstructor = 3322 final bool isSymbolConstructor =
3321 closedWorld.commonElements.isSymbolConstructor(constructorDeclaration); 3323 closedWorld.commonElements.isSymbolConstructor(constructorDeclaration);
3322 final bool isJSArrayTypedConstructor = 3324 final bool isJSArrayTypedConstructor = constructorDeclaration ==
3323 constructorDeclaration == helpers.jsArrayTypedConstructor; 3325 closedWorld.commonElements.jsArrayTypedConstructor;
3324 3326
3325 if (isSymbolConstructor) { 3327 if (isSymbolConstructor) {
3326 constructor = helpers.symbolValidatedConstructor; 3328 constructor = commonElements.symbolValidatedConstructor;
3327 assert(invariant(send, constructor != null, 3329 assert(invariant(send, constructor != null,
3328 message: 'Constructor Symbol.validated is missing')); 3330 message: 'Constructor Symbol.validated is missing'));
3329 callStructure = helpers.symbolValidatedConstructorSelector.callStructure; 3331 callStructure =
3332 commonElements.symbolValidatedConstructorSelector.callStructure;
3330 assert(invariant(send, callStructure != null, 3333 assert(invariant(send, callStructure != null,
3331 message: 'Constructor Symbol.validated is missing')); 3334 message: 'Constructor Symbol.validated is missing'));
3332 } 3335 }
3333 3336
3334 bool isRedirected = constructorDeclaration.isRedirectingFactory; 3337 bool isRedirected = constructorDeclaration.isRedirectingFactory;
3335 if (!constructorDeclaration.isCyclicRedirection) { 3338 if (!constructorDeclaration.isCyclicRedirection) {
3336 // Insert a check for every deferred redirection on the path to the 3339 // Insert a check for every deferred redirection on the path to the
3337 // final target. 3340 // final target.
3338 ConstructorElement target = constructorDeclaration; 3341 ConstructorElement target = constructorDeclaration;
3339 while (target.isRedirectingFactory) { 3342 while (target.isRedirectingFactory) {
(...skipping 406 matching lines...) Expand 10 before | Expand all | Expand 10 after
3746 ast.Send node, ResolutionTypeVariableType typeVariable) { 3749 ast.Send node, ResolutionTypeVariableType typeVariable) {
3747 // GENERIC_METHODS: This provides thin support for method type variables 3750 // GENERIC_METHODS: This provides thin support for method type variables
3748 // by treating them as malformed when evaluated as a literal. For full 3751 // by treating them as malformed when evaluated as a literal. For full
3749 // support of generic methods this must be revised. 3752 // support of generic methods this must be revised.
3750 if (typeVariable is MethodTypeVariableType) { 3753 if (typeVariable is MethodTypeVariableType) {
3751 generateTypeError(node, "Method type variables are not reified"); 3754 generateTypeError(node, "Method type variables are not reified");
3752 } else { 3755 } else {
3753 ResolutionDartType type = localsHandler.substInContext(typeVariable); 3756 ResolutionDartType type = localsHandler.substInContext(typeVariable);
3754 HInstruction value = typeBuilder.analyzeTypeArgument(type, sourceElement, 3757 HInstruction value = typeBuilder.analyzeTypeArgument(type, sourceElement,
3755 sourceInformation: sourceInformationBuilder.buildGet(node)); 3758 sourceInformation: sourceInformationBuilder.buildGet(node));
3756 pushInvokeStatic(node, helpers.runtimeTypeToString, [value], 3759 pushInvokeStatic(node, commonElements.runtimeTypeToString, [value],
3757 typeMask: commonMasks.stringType); 3760 typeMask: commonMasks.stringType);
3758 pushInvokeStatic(node, helpers.createRuntimeType, [pop()]); 3761 pushInvokeStatic(node, commonElements.createRuntimeType, [pop()]);
3759 } 3762 }
3760 } 3763 }
3761 3764
3762 /// Generate a call to a type literal. 3765 /// Generate a call to a type literal.
3763 void generateTypeLiteralCall(ast.Send node) { 3766 void generateTypeLiteralCall(ast.Send node) {
3764 // This send is of the form 'e(...)', where e is resolved to a type 3767 // This send is of the form 'e(...)', where e is resolved to a type
3765 // reference. We create a regular closure call on the result of the type 3768 // reference. We create a regular closure call on the result of the type
3766 // reference instead of creating a NoSuchMethodError to avoid pulling it 3769 // reference instead of creating a NoSuchMethodError to avoid pulling it
3767 // in if it is not used (e.g., in a try/catch). 3770 // in if it is not used (e.g., in a try/catch).
3768 HInstruction target = pop(); 3771 HInstruction target = pop();
(...skipping 20 matching lines...) Expand all
3789 internalError(Spannable node, String reason) { 3792 internalError(Spannable node, String reason) {
3790 reporter.internalError(node, reason); 3793 reporter.internalError(node, reason);
3791 } 3794 }
3792 3795
3793 void generateError(ast.Node node, String message, Element helper) { 3796 void generateError(ast.Node node, String message, Element helper) {
3794 HInstruction errorMessage = addConstantString(message); 3797 HInstruction errorMessage = addConstantString(message);
3795 pushInvokeStatic(node, helper, [errorMessage]); 3798 pushInvokeStatic(node, helper, [errorMessage]);
3796 } 3799 }
3797 3800
3798 void generateRuntimeError(ast.Node node, String message) { 3801 void generateRuntimeError(ast.Node node, String message) {
3799 MethodElement helper = helpers.throwRuntimeError; 3802 MethodElement helper = commonElements.throwRuntimeError;
3800 generateError(node, message, helper); 3803 generateError(node, message, helper);
3801 } 3804 }
3802 3805
3803 void generateTypeError(ast.Node node, String message) { 3806 void generateTypeError(ast.Node node, String message) {
3804 MethodElement helper = helpers.throwTypeError; 3807 MethodElement helper = commonElements.throwTypeError;
3805 generateError(node, message, helper); 3808 generateError(node, message, helper);
3806 } 3809 }
3807 3810
3808 void generateAbstractClassInstantiationError(ast.Node node, String message) { 3811 void generateAbstractClassInstantiationError(ast.Node node, String message) {
3809 MethodElement helper = helpers.throwAbstractClassInstantiationError; 3812 MethodElement helper = commonElements.throwAbstractClassInstantiationError;
3810 generateError(node, message, helper); 3813 generateError(node, message, helper);
3811 } 3814 }
3812 3815
3813 void generateThrowNoSuchMethod(ast.Node diagnosticNode, String methodName, 3816 void generateThrowNoSuchMethod(ast.Node diagnosticNode, String methodName,
3814 {Link<ast.Node> argumentNodes, 3817 {Link<ast.Node> argumentNodes,
3815 List<HInstruction> argumentValues, 3818 List<HInstruction> argumentValues,
3816 List<String> existingArguments, 3819 List<String> existingArguments,
3817 SourceInformation sourceInformation}) { 3820 SourceInformation sourceInformation}) {
3818 MethodElement helper = helpers.throwNoSuchMethod; 3821 MethodElement helper = commonElements.throwNoSuchMethod;
3819 ConstantValue receiverConstant = 3822 ConstantValue receiverConstant =
3820 constantSystem.createString(new ast.DartString.empty()); 3823 constantSystem.createString(new ast.DartString.empty());
3821 HInstruction receiver = graph.addConstant(receiverConstant, closedWorld); 3824 HInstruction receiver = graph.addConstant(receiverConstant, closedWorld);
3822 ast.DartString dartString = new ast.DartString.literal(methodName); 3825 ast.DartString dartString = new ast.DartString.literal(methodName);
3823 ConstantValue nameConstant = constantSystem.createString(dartString); 3826 ConstantValue nameConstant = constantSystem.createString(dartString);
3824 HInstruction name = graph.addConstant(nameConstant, closedWorld); 3827 HInstruction name = graph.addConstant(nameConstant, closedWorld);
3825 if (argumentValues == null) { 3828 if (argumentValues == null) {
3826 argumentValues = <HInstruction>[]; 3829 argumentValues = <HInstruction>[];
3827 argumentNodes.forEach((argumentNode) { 3830 argumentNodes.forEach((argumentNode) {
3828 visit(argumentNode); 3831 visit(argumentNode);
(...skipping 94 matching lines...) Expand 10 before | Expand all | Expand 10 after
3923 List<HInstruction> arguments, 3926 List<HInstruction> arguments,
3924 {SourceInformation sourceInformation}) { 3927 {SourceInformation sourceInformation}) {
3925 // We prefer to not inline certain operations on indexables, 3928 // We prefer to not inline certain operations on indexables,
3926 // because the constant folder will handle them better and turn 3929 // because the constant folder will handle them better and turn
3927 // them into simpler instructions that allow further 3930 // them into simpler instructions that allow further
3928 // optimizations. 3931 // optimizations.
3929 bool isOptimizableOperationOnIndexable(Selector selector, Element element) { 3932 bool isOptimizableOperationOnIndexable(Selector selector, Element element) {
3930 bool isLength = selector.isGetter && selector.name == "length"; 3933 bool isLength = selector.isGetter && selector.name == "length";
3931 if (isLength || selector.isIndex) { 3934 if (isLength || selector.isIndex) {
3932 return closedWorld.isSubtypeOf( 3935 return closedWorld.isSubtypeOf(
3933 element.enclosingClass, helpers.jsIndexableClass); 3936 element.enclosingClass, commonElements.jsIndexableClass);
3934 } else if (selector.isIndexSet) { 3937 } else if (selector.isIndexSet) {
3935 return closedWorld.isSubtypeOf( 3938 return closedWorld.isSubtypeOf(
3936 element.enclosingClass, helpers.jsMutableIndexableClass); 3939 element.enclosingClass, commonElements.jsMutableIndexableClass);
3937 } else { 3940 } else {
3938 return false; 3941 return false;
3939 } 3942 }
3940 } 3943 }
3941 3944
3942 bool isOptimizableOperation(Selector selector, Element element) { 3945 bool isOptimizableOperation(Selector selector, Element element) {
3943 ClassElement cls = element.enclosingClass; 3946 ClassElement cls = element.enclosingClass;
3944 if (isOptimizableOperationOnIndexable(selector, element)) return true; 3947 if (isOptimizableOperationOnIndexable(selector, element)) return true;
3945 if (!interceptorData.interceptedClasses.contains(cls)) return false; 3948 if (!interceptorData.interceptedClasses.contains(cls)) return false;
3946 if (selector.isOperator) return true; 3949 if (selector.isOperator) return true;
3947 if (selector.isSetter) return true; 3950 if (selector.isSetter) return true;
3948 if (selector.isIndex) return true; 3951 if (selector.isIndex) return true;
3949 if (selector.isIndexSet) return true; 3952 if (selector.isIndexSet) return true;
3950 if (element == helpers.jsArrayAdd || 3953 if (element == commonElements.jsArrayAdd ||
3951 element == helpers.jsArrayRemoveLast || 3954 element == commonElements.jsArrayRemoveLast ||
3952 element == helpers.jsStringSplit) { 3955 element == commonElements.jsStringSplit) {
3953 return true; 3956 return true;
3954 } 3957 }
3955 return false; 3958 return false;
3956 } 3959 }
3957 3960
3958 MemberElement element = closedWorld.locateSingleElement(selector, mask); 3961 MemberElement element = closedWorld.locateSingleElement(selector, mask);
3959 if (element != null && 3962 if (element != null &&
3960 !element.isField && 3963 !element.isField &&
3961 !(element.isGetter && selector.isCall) && 3964 !(element.isGetter && selector.isCall) &&
3962 !(element.isFunction && selector.isGetter) && 3965 !(element.isFunction && selector.isGetter) &&
(...skipping 95 matching lines...) Expand 10 before | Expand all | Expand 10 after
4058 if (type is ResolutionInterfaceType && 4061 if (type is ResolutionInterfaceType &&
4059 nativeData.isNativeClass(type.element)) { 4062 nativeData.isNativeClass(type.element)) {
4060 nativeBehavior.typesInstantiated.add(type); 4063 nativeBehavior.typesInstantiated.add(type);
4061 } 4064 }
4062 4065
4063 // It also includes any other JS interop type if we don't trust the 4066 // It also includes any other JS interop type if we don't trust the
4064 // annotation or if is declared too broad. 4067 // annotation or if is declared too broad.
4065 if (!options.trustJSInteropTypeAnnotations || 4068 if (!options.trustJSInteropTypeAnnotations ||
4066 type.isObject || 4069 type.isObject ||
4067 type.isDynamic) { 4070 type.isDynamic) {
4068 ClassElement cls = helpers.jsJavaScriptObjectClass; 4071 ClassElement cls = commonElements.jsJavaScriptObjectClass;
4069 nativeBehavior.typesInstantiated.add(cls.thisType); 4072 nativeBehavior.typesInstantiated.add(cls.thisType);
4070 } 4073 }
4071 4074
4072 String code; 4075 String code;
4073 if (element.isGetter) { 4076 if (element.isGetter) {
4074 code = "#"; 4077 code = "#";
4075 } else if (element.isSetter) { 4078 } else if (element.isSetter) {
4076 code = "# = #"; 4079 code = "# = #";
4077 } else { 4080 } else {
4078 var args = new List.filled(arguments.length, '#').join(','); 4081 var args = new List.filled(arguments.length, '#').join(',');
(...skipping 1225 matching lines...) Expand 10 before | Expand all | Expand 10 after
5304 } 5307 }
5305 return new JumpHandler(this, element); 5308 return new JumpHandler(this, element);
5306 } 5309 }
5307 5310
5308 visitAsyncForIn(ast.AsyncForIn node) { 5311 visitAsyncForIn(ast.AsyncForIn node) {
5309 // The async-for is implemented with a StreamIterator. 5312 // The async-for is implemented with a StreamIterator.
5310 HInstruction streamIterator; 5313 HInstruction streamIterator;
5311 5314
5312 visit(node.expression); 5315 visit(node.expression);
5313 HInstruction expression = pop(); 5316 HInstruction expression = pop();
5314 ConstructorElement constructor = helpers.streamIteratorConstructor; 5317 ConstructorElement constructor = commonElements.streamIteratorConstructor;
5315 pushInvokeStatic( 5318 pushInvokeStatic(
5316 node, constructor, [expression, graph.addConstantNull(closedWorld)]); 5319 node, constructor, [expression, graph.addConstantNull(closedWorld)]);
5317 streamIterator = pop(); 5320 streamIterator = pop();
5318 5321
5319 void buildInitializer() {} 5322 void buildInitializer() {}
5320 5323
5321 HInstruction buildCondition() { 5324 HInstruction buildCondition() {
5322 Selector selector = Selectors.moveNext; 5325 Selector selector = Selectors.moveNext;
5323 TypeMask mask = elementInferenceResults.typeOfIteratorMoveNext(node); 5326 TypeMask mask = elementInferenceResults.typeOfIteratorMoveNext(node);
5324 pushInvokeDynamic(node, selector, mask, [streamIterator]); 5327 pushInvokeDynamic(node, selector, mask, [streamIterator]);
(...skipping 47 matching lines...) Expand 10 before | Expand all | Expand 10 after
5372 5375
5373 // This scheme recognizes for-in on direct lists. It does not recognize all 5376 // This scheme recognizes for-in on direct lists. It does not recognize all
5374 // uses of ArrayIterator. They still occur when the receiver is an Iterable 5377 // uses of ArrayIterator. They still occur when the receiver is an Iterable
5375 // with a `get iterator` method that delegates to another Iterable and the 5378 // with a `get iterator` method that delegates to another Iterable and the
5376 // method is inlined. We would require full scalar replacement in that 5379 // method is inlined. We would require full scalar replacement in that
5377 // case. 5380 // case.
5378 5381
5379 TypeMask mask = elementInferenceResults.typeOfIterator(node); 5382 TypeMask mask = elementInferenceResults.typeOfIterator(node);
5380 5383
5381 if (mask != null && 5384 if (mask != null &&
5382 mask.satisfies(helpers.jsIndexableClass, closedWorld) && 5385 mask.satisfies(commonElements.jsIndexableClass, closedWorld) &&
5383 // String is indexable but not iterable. 5386 // String is indexable but not iterable.
5384 !mask.satisfies(helpers.jsStringClass, closedWorld)) { 5387 !mask.satisfies(commonElements.jsStringClass, closedWorld)) {
5385 return buildSyncForInIndexable(node, mask); 5388 return buildSyncForInIndexable(node, mask);
5386 } 5389 }
5387 buildSyncForInIterator(node); 5390 buildSyncForInIterator(node);
5388 } 5391 }
5389 5392
5390 buildSyncForInIterator(ast.SyncForIn node) { 5393 buildSyncForInIterator(ast.SyncForIn node) {
5391 // Generate a structure equivalent to: 5394 // Generate a structure equivalent to:
5392 // Iterator<E> $iter = <iterable>.iterator; 5395 // Iterator<E> $iter = <iterable>.iterator;
5393 // while ($iter.moveNext()) { 5396 // while ($iter.moveNext()) {
5394 // <declaredIdentifier> = $iter.current; 5397 // <declaredIdentifier> = $iter.current;
(...skipping 77 matching lines...) Expand 10 before | Expand all | Expand 10 after
5472 5475
5473 void buildConcurrentModificationErrorCheck() { 5476 void buildConcurrentModificationErrorCheck() {
5474 if (originalLength == null) return; 5477 if (originalLength == null) return;
5475 // The static call checkConcurrentModificationError() is expanded in 5478 // The static call checkConcurrentModificationError() is expanded in
5476 // codegen to: 5479 // codegen to:
5477 // 5480 //
5478 // array.length == _end || throwConcurrentModificationError(array) 5481 // array.length == _end || throwConcurrentModificationError(array)
5479 // 5482 //
5480 HInstruction length = buildGetLength(); 5483 HInstruction length = buildGetLength();
5481 push(new HIdentity(length, originalLength, null, boolType)); 5484 push(new HIdentity(length, originalLength, null, boolType));
5482 pushInvokeStatic( 5485 pushInvokeStatic(node, commonElements.checkConcurrentModificationError,
5483 node, helpers.checkConcurrentModificationError, [pop(), array]); 5486 [pop(), array]);
5484 pop(); 5487 pop();
5485 } 5488 }
5486 5489
5487 void buildInitializer() { 5490 void buildInitializer() {
5488 visit(node.expression); 5491 visit(node.expression);
5489 array = pop(); 5492 array = pop();
5490 isFixed = isFixedLength(array.instructionType, closedWorld); 5493 isFixed = isFixedLength(array.instructionType, closedWorld);
5491 localsHandler.updateLocal( 5494 localsHandler.updateLocal(
5492 indexVariable, graph.addConstantInt(0, closedWorld)); 5495 indexVariable, graph.addConstantInt(0, closedWorld));
5493 originalLength = buildGetLength(); 5496 originalLength = buildGetLength();
(...skipping 107 matching lines...) Expand 10 before | Expand all | Expand 10 after
5601 link = link.tail) { 5604 link = link.tail) {
5602 visit(link.head); 5605 visit(link.head);
5603 listInputs.add(pop()); 5606 listInputs.add(pop());
5604 listInputs.add(pop()); 5607 listInputs.add(pop());
5605 } 5608 }
5606 5609
5607 ConstructorElement listConstructor; 5610 ConstructorElement listConstructor;
5608 List<HInstruction> inputs = <HInstruction>[]; 5611 List<HInstruction> inputs = <HInstruction>[];
5609 5612
5610 if (listInputs.isEmpty) { 5613 if (listInputs.isEmpty) {
5611 listConstructor = helpers.mapLiteralConstructorEmpty; 5614 listConstructor = commonElements.mapLiteralConstructorEmpty;
5612 } else { 5615 } else {
5613 listConstructor = helpers.mapLiteralConstructor; 5616 listConstructor = commonElements.mapLiteralConstructor;
5614 HLiteralList keyValuePairs = buildLiteralList(listInputs); 5617 HLiteralList keyValuePairs = buildLiteralList(listInputs);
5615 add(keyValuePairs); 5618 add(keyValuePairs);
5616 inputs.add(keyValuePairs); 5619 inputs.add(keyValuePairs);
5617 } 5620 }
5618 5621
5619 assert(listConstructor.isFactoryConstructor); 5622 assert(listConstructor.isFactoryConstructor);
5620 5623
5621 ConstructorElement constructorElement = listConstructor; 5624 ConstructorElement constructorElement = listConstructor;
5622 listConstructor = constructorElement.effectiveTarget; 5625 listConstructor = constructorElement.effectiveTarget;
5623 5626
5624 ResolutionInterfaceType type = elements.getType(node); 5627 ResolutionInterfaceType type = elements.getType(node);
5625 ResolutionInterfaceType expectedType = 5628 ResolutionInterfaceType expectedType =
5626 constructorElement.computeEffectiveTargetType(type); 5629 constructorElement.computeEffectiveTargetType(type);
5627 expectedType = localsHandler.substInContext(expectedType); 5630 expectedType = localsHandler.substInContext(expectedType);
5628 5631
5629 ClassElement cls = listConstructor.enclosingClass; 5632 ClassElement cls = listConstructor.enclosingClass;
5630 5633
5631 MethodElement createFunction = listConstructor; 5634 MethodElement createFunction = listConstructor;
5632 if (rtiNeed.classNeedsRti(cls)) { 5635 if (rtiNeed.classNeedsRti(cls)) {
5633 List<HInstruction> typeInputs = <HInstruction>[]; 5636 List<HInstruction> typeInputs = <HInstruction>[];
5634 expectedType.typeArguments.forEach((ResolutionDartType argument) { 5637 expectedType.typeArguments.forEach((ResolutionDartType argument) {
5635 typeInputs 5638 typeInputs
5636 .add(typeBuilder.analyzeTypeArgument(argument, sourceElement)); 5639 .add(typeBuilder.analyzeTypeArgument(argument, sourceElement));
5637 }); 5640 });
5638 5641
5639 // We lift this common call pattern into a helper function to save space 5642 // We lift this common call pattern into a helper function to save space
5640 // in the output. 5643 // in the output.
5641 if (typeInputs.every((HInstruction input) => input.isNull())) { 5644 if (typeInputs.every((HInstruction input) => input.isNull())) {
5642 if (listInputs.isEmpty) { 5645 if (listInputs.isEmpty) {
5643 createFunction = helpers.mapLiteralUntypedEmptyMaker; 5646 createFunction = commonElements.mapLiteralUntypedEmptyMaker;
5644 } else { 5647 } else {
5645 createFunction = helpers.mapLiteralUntypedMaker; 5648 createFunction = commonElements.mapLiteralUntypedMaker;
5646 } 5649 }
5647 } else { 5650 } else {
5648 inputs.addAll(typeInputs); 5651 inputs.addAll(typeInputs);
5649 } 5652 }
5650 } 5653 }
5651 5654
5652 // If rti is needed and the map literal has no type parameters, 5655 // If rti is needed and the map literal has no type parameters,
5653 // 'constructor' is a static function that forwards the call to the factory 5656 // 'constructor' is a static function that forwards the call to the factory
5654 // constructor without type parameters. 5657 // constructor without type parameters.
5655 assert(createFunction is ConstructorElement || 5658 assert(createFunction is ConstructorElement ||
5656 createFunction is FunctionElement); 5659 createFunction is FunctionElement);
5657 5660
5658 // The instruction type will always be a subtype of the mapLiteralClass, but 5661 // The instruction type will always be a subtype of the mapLiteralClass, but
5659 // type inference might discover a more specific type, or find nothing (in 5662 // type inference might discover a more specific type, or find nothing (in
5660 // dart2js unit tests). 5663 // dart2js unit tests).
5661 TypeMask mapType = 5664 TypeMask mapType = new TypeMask.nonNullSubtype(
5662 new TypeMask.nonNullSubtype(helpers.mapLiteralClass, closedWorld); 5665 commonElements.mapLiteralClass, closedWorld);
5663 TypeMask returnTypeMask = TypeMaskFactory.inferredReturnTypeForElement( 5666 TypeMask returnTypeMask = TypeMaskFactory.inferredReturnTypeForElement(
5664 createFunction, globalInferenceResults); 5667 createFunction, globalInferenceResults);
5665 TypeMask instructionType = 5668 TypeMask instructionType =
5666 mapType.intersection(returnTypeMask, closedWorld); 5669 mapType.intersection(returnTypeMask, closedWorld);
5667 5670
5668 addInlinedInstantiation(expectedType); 5671 addInlinedInstantiation(expectedType);
5669 pushInvokeStatic(node, createFunction, inputs, 5672 pushInvokeStatic(node, createFunction, inputs,
5670 typeMask: instructionType, instanceType: expectedType); 5673 typeMask: instructionType, instanceType: expectedType);
5671 removeInlinedInstantiation(expectedType); 5674 removeInlinedInstantiation(expectedType);
5672 } 5675 }
(...skipping 286 matching lines...) Expand 10 before | Expand all | Expand 10 after
5959 // An HSwitch has n inputs and n+1 successors, the last being the 5962 // An HSwitch has n inputs and n+1 successors, the last being the
5960 // default case. 5963 // default case.
5961 expressionEnd.addSuccessor(block); 5964 expressionEnd.addSuccessor(block);
5962 hasDefault = true; 5965 hasDefault = true;
5963 } 5966 }
5964 open(block); 5967 open(block);
5965 localsHandler = new LocalsHandler.from(savedLocals); 5968 localsHandler = new LocalsHandler.from(savedLocals);
5966 buildSwitchCase(switchCase); 5969 buildSwitchCase(switchCase);
5967 if (!isAborted()) { 5970 if (!isAborted()) {
5968 if (caseIterator.hasNext && isReachable) { 5971 if (caseIterator.hasNext && isReachable) {
5969 pushInvokeStatic(switchCase, helpers.fallThroughError, []); 5972 pushInvokeStatic(switchCase, commonElements.fallThroughError, []);
5970 HInstruction error = pop(); 5973 HInstruction error = pop();
5971 closeAndGotoExit(new HThrow(error, error.sourceInformation)); 5974 closeAndGotoExit(new HThrow(error, error.sourceInformation));
5972 } else if (!isDefaultCase(switchCase)) { 5975 } else if (!isDefaultCase(switchCase)) {
5973 // If there is no default, we will add one later to avoid 5976 // If there is no default, we will add one later to avoid
5974 // the critical edge. So we generate a break statement to make 5977 // the critical edge. So we generate a break statement to make
5975 // sure the last case does not fall through to the default case. 5978 // sure the last case does not fall through to the default case.
5976 jumpHandler.generateBreak(); 5979 jumpHandler.generateBreak();
5977 } 5980 }
5978 } 5981 }
5979 statements.add( 5982 statements.add(
(...skipping 199 matching lines...) Expand 10 before | Expand all | Expand 10 after
6179 startCatchBlock = graph.addNewBlock(); 6182 startCatchBlock = graph.addNewBlock();
6180 open(startCatchBlock); 6183 open(startCatchBlock);
6181 // Note that the name of this local is irrelevant. 6184 // Note that the name of this local is irrelevant.
6182 SyntheticLocal local = 6185 SyntheticLocal local =
6183 new SyntheticLocal('exception', localsHandler.executableContext); 6186 new SyntheticLocal('exception', localsHandler.executableContext);
6184 exception = new HLocalValue(local, commonMasks.nonNullType); 6187 exception = new HLocalValue(local, commonMasks.nonNullType);
6185 add(exception); 6188 add(exception);
6186 HInstruction oldRethrowableException = rethrowableException; 6189 HInstruction oldRethrowableException = rethrowableException;
6187 rethrowableException = exception; 6190 rethrowableException = exception;
6188 6191
6189 pushInvokeStatic(node, helpers.exceptionUnwrapper, [exception]); 6192 pushInvokeStatic(node, commonElements.exceptionUnwrapper, [exception]);
6190 HInvokeStatic unwrappedException = pop(); 6193 HInvokeStatic unwrappedException = pop();
6191 tryInstruction.exception = exception; 6194 tryInstruction.exception = exception;
6192 Link<ast.Node> link = node.catchBlocks.nodes; 6195 Link<ast.Node> link = node.catchBlocks.nodes;
6193 6196
6194 void pushCondition(ast.CatchBlock catchBlock) { 6197 void pushCondition(ast.CatchBlock catchBlock) {
6195 if (catchBlock.onKeyword != null) { 6198 if (catchBlock.onKeyword != null) {
6196 ResolutionDartType type = elements.getType(catchBlock.type); 6199 ResolutionDartType type = elements.getType(catchBlock.type);
6197 if (type == null) { 6200 if (type == null) {
6198 reporter.internalError(catchBlock.type, 'On with no type.'); 6201 reporter.internalError(catchBlock.type, 'On with no type.');
6199 } 6202 }
(...skipping 24 matching lines...) Expand all
6224 void visitThen() { 6227 void visitThen() {
6225 ast.CatchBlock catchBlock = link.head; 6228 ast.CatchBlock catchBlock = link.head;
6226 link = link.tail; 6229 link = link.tail;
6227 if (catchBlock.exception != null) { 6230 if (catchBlock.exception != null) {
6228 LocalVariableElement exceptionVariable = 6231 LocalVariableElement exceptionVariable =
6229 elements[catchBlock.exception]; 6232 elements[catchBlock.exception];
6230 localsHandler.updateLocal(exceptionVariable, unwrappedException); 6233 localsHandler.updateLocal(exceptionVariable, unwrappedException);
6231 } 6234 }
6232 ast.Node trace = catchBlock.trace; 6235 ast.Node trace = catchBlock.trace;
6233 if (trace != null) { 6236 if (trace != null) {
6234 pushInvokeStatic(trace, helpers.traceFromException, [exception]); 6237 pushInvokeStatic(
6238 trace, commonElements.traceFromException, [exception]);
6235 HInstruction traceInstruction = pop(); 6239 HInstruction traceInstruction = pop();
6236 LocalVariableElement traceVariable = elements[trace]; 6240 LocalVariableElement traceVariable = elements[trace];
6237 localsHandler.updateLocal(traceVariable, traceInstruction); 6241 localsHandler.updateLocal(traceVariable, traceInstruction);
6238 } 6242 }
6239 visit(catchBlock); 6243 visit(catchBlock);
6240 } 6244 }
6241 6245
6242 void visitElse() { 6246 void visitElse() {
6243 if (link.isEmpty) { 6247 if (link.isEmpty) {
6244 closeAndGotoExit(new HThrow(exception, exception.sourceInformation, 6248 closeAndGotoExit(new HThrow(exception, exception.sourceInformation,
(...skipping 496 matching lines...) Expand 10 before | Expand all | Expand 10 after
6741 this.oldReturnLocal, 6745 this.oldReturnLocal,
6742 this.oldReturnType, 6746 this.oldReturnType,
6743 this.oldResolvedAst, 6747 this.oldResolvedAst,
6744 this.oldStack, 6748 this.oldStack,
6745 this.oldLocalsHandler, 6749 this.oldLocalsHandler,
6746 this.inTryStatement, 6750 this.inTryStatement,
6747 this.allFunctionsCalledOnce, 6751 this.allFunctionsCalledOnce,
6748 this.oldElementInferenceResults) 6752 this.oldElementInferenceResults)
6749 : super(function); 6753 : super(function);
6750 } 6754 }
OLDNEW
« no previous file with comments | « pkg/compiler/lib/src/patch_parser.dart ('k') | pkg/compiler/lib/src/ssa/builder_kernel.dart » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698