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

Side by Side Diff: lib/src/codegen/js_codegen.dart

Issue 1093353004: fix list initializers (Closed) Base URL: git@github.com:dart-lang/dev_compiler.git@master
Patch Set: baselines Created 5 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 | « lib/runtime/dart_runtime.js ('k') | lib/src/dependency_graph.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) 2015, the Dart project authors. Please see the AUTHORS file 1 // Copyright (c) 2015, the Dart project authors. Please see the AUTHORS file
2 // for details. All rights reserved. Use of this source code is governed by a 2 // for details. All rights reserved. Use of this source code is governed by a
3 // BSD-style license that can be found in the LICENSE file. 3 // BSD-style license that can be found in the LICENSE file.
4 4
5 library dev_compiler.src.codegen.js_codegen; 5 library dev_compiler.src.codegen.js_codegen;
6 6
7 import 'dart:collection' show HashSet, HashMap; 7 import 'dart:collection' show HashSet, HashMap;
8 8
9 import 'package:analyzer/analyzer.dart' hide ConstantEvaluator; 9 import 'package:analyzer/analyzer.dart' hide ConstantEvaluator;
10 import 'package:analyzer/src/generated/ast.dart' hide ConstantEvaluator; 10 import 'package:analyzer/src/generated/ast.dart' hide ConstantEvaluator;
11 import 'package:analyzer/src/generated/constant.dart'; 11 import 'package:analyzer/src/generated/constant.dart';
12 import 'package:analyzer/src/generated/element.dart'; 12 import 'package:analyzer/src/generated/element.dart';
13 import 'package:analyzer/src/generated/resolver.dart' show TypeProvider; 13 import 'package:analyzer/src/generated/resolver.dart' show TypeProvider;
14 import 'package:analyzer/src/generated/scanner.dart' 14 import 'package:analyzer/src/generated/scanner.dart'
15 show StringToken, Token, TokenType; 15 show StringToken, Token, TokenType;
16 import 'package:path/path.dart' as path; 16 import 'package:path/path.dart' as path;
17 17
18 import 'package:dev_compiler/src/codegen/ast_builder.dart' show AstBuilder; 18 import 'package:dev_compiler/src/codegen/ast_builder.dart' show AstBuilder;
19 import 'package:dev_compiler/src/codegen/reify_coercions.dart' 19 import 'package:dev_compiler/src/codegen/reify_coercions.dart'
20 show CoercionReifier; 20 show CoercionReifier;
21 21
22 // TODO(jmesserly): import from its own package 22 // TODO(jmesserly): import from its own package
23 import 'package:dev_compiler/src/js/js_ast.dart' as JS; 23 import 'package:dev_compiler/src/js/js_ast.dart' as JS;
24 import 'package:dev_compiler/src/js/js_ast.dart' show js; 24 import 'package:dev_compiler/src/js/js_ast.dart' show js;
25 25
26 import 'package:dev_compiler/src/checker/rules.dart'; 26 import 'package:dev_compiler/src/checker/rules.dart';
27 import 'package:dev_compiler/src/dependency_graph.dart';
27 import 'package:dev_compiler/src/info.dart'; 28 import 'package:dev_compiler/src/info.dart';
28 import 'package:dev_compiler/src/options.dart'; 29 import 'package:dev_compiler/src/options.dart';
29 import 'package:dev_compiler/src/utils.dart'; 30 import 'package:dev_compiler/src/utils.dart';
30 31
31 import 'code_generator.dart'; 32 import 'code_generator.dart';
32 import 'js_field_storage.dart'; 33 import 'js_field_storage.dart';
33 import 'js_names.dart' show JSTemporary, invalidJSStaticMethodName; 34 import 'js_names.dart' show JSTemporary, invalidJSStaticMethodName;
34 import 'js_metalet.dart'; 35 import 'js_metalet.dart';
35 import 'js_printer.dart' show writeJsLibrary; 36 import 'js_printer.dart' show writeJsLibrary;
36 import 'side_effect_analysis.dart'; 37 import 'side_effect_analysis.dart';
(...skipping 395 matching lines...) Expand 10 before | Expand all | Expand 10 after
432 433
433 if (type is InterfaceType) { 434 if (type is InterfaceType) {
434 result = _typeMightNotBeLoaded(type.superclass) || 435 result = _typeMightNotBeLoaded(type.superclass) ||
435 type.mixins.any(_typeMightNotBeLoaded); 436 type.mixins.any(_typeMightNotBeLoaded);
436 } else if (type is FunctionType) { 437 } else if (type is FunctionType) {
437 result = _typeMightNotBeLoaded(types.functionType); 438 result = _typeMightNotBeLoaded(types.functionType);
438 } 439 }
439 return _lazyClassMemo[type.element] = result; 440 return _lazyClassMemo[type.element] = result;
440 } 441 }
441 442
442 /// Curated order to minimize lazy classes needed by dart:core and its
443 /// transitive SDK imports.
444 static const CORELIB_ORDER = const [
445 'dart.core',
446 'dart.collection',
447 'dart._internal'
448 ];
449
450 /// Returns true if the class might not be loaded. 443 /// Returns true if the class might not be loaded.
451 /// 444 ///
452 /// If the class is from our library, this can happen because it's lazy. 445 /// If the class is from our library, this can happen because it's lazy.
453 /// 446 ///
454 /// If the class is from a different library, it could happen if we're in 447 /// If the class is from a different library, it could happen if we're in
455 /// a library cycle. In other words, if that different library depends back 448 /// a library cycle. In other words, if that different library depends back
456 /// on this library via some transitive import path. 449 /// on this library via some transitive import path.
457 /// 450 ///
458 /// If we could control the global import ordering, we could eliminate some 451 /// If we could control the global import ordering, we could eliminate some
459 /// of these cases, by ordering the imports of the cyclic libraries in an 452 /// of these cases, by ordering the imports of the cyclic libraries in an
460 /// optimal way. For example, we could order the libraries in a cycle to 453 /// optimal way. For example, we could order the libraries in a cycle to
461 /// minimize laziness. However, we currently assume we cannot control the 454 /// minimize laziness. However, we currently assume we cannot control the
462 /// order that the cycle of libraries will be loaded in. 455 /// order that the cycle of libraries will be loaded in.
463 bool _typeMightNotBeLoaded(DartType type) { 456 bool _typeMightNotBeLoaded(DartType type) {
464 var library = type.element.library; 457 var library = type.element.library;
465 if (library == currentLibrary) return _lazyClass(type); 458 if (library == currentLibrary) return _lazyClass(type);
466 459
467 // The SDK is a special case: we optimize the order to prevent laziness. 460 // The SDK is a special case: we optimize the order to prevent laziness.
468 if (library.isInSdk) { 461 if (library.isInSdk) {
469 // SDK is loaded before non-SDK libraies 462 // SDK is loaded before non-SDK libraies
470 if (!currentLibrary.isInSdk) return false; 463 if (!currentLibrary.isInSdk) return false;
471 464
472 // Compute the order of both SDK libraries. If unknown, assume it's after. 465 // Compute the order of both SDK libraries. If unknown, assume it's after.
473 var classOrder = CORELIB_ORDER.indexOf(library.name); 466 var classOrder = corelibOrder.indexOf(library.name);
474 if (classOrder == -1) classOrder = CORELIB_ORDER.length; 467 if (classOrder == -1) classOrder = corelibOrder.length;
475 468
476 var currentOrder = CORELIB_ORDER.indexOf(currentLibrary.name); 469 var currentOrder = corelibOrder.indexOf(currentLibrary.name);
477 if (currentOrder == -1) currentOrder = CORELIB_ORDER.length; 470 if (currentOrder == -1) currentOrder = corelibOrder.length;
478 471
479 // If the dart:* library we are currently compiling is loaded after the 472 // If the dart:* library we are currently compiling is loaded after the
480 // class's library, then we know the class is available. 473 // class's library, then we know the class is available.
481 if (classOrder != currentOrder) return currentOrder < classOrder; 474 if (classOrder != currentOrder) return currentOrder < classOrder;
482 475
483 // If we don't know the order of the class's library or the current 476 // If we don't know the order of the class's library or the current
484 // library, do the normal cycle check. (Not all SDK libs are cycles.) 477 // library, do the normal cycle check. (Not all SDK libs are cycles.)
485 } 478 }
486 479
487 return _inLibraryCycle(library); 480 return _inLibraryCycle(library);
(...skipping 1564 matching lines...) Expand 10 before | Expand all | Expand 10 after
2052 visitIntegerLiteral(IntegerLiteral node) => js.number(node.value); 2045 visitIntegerLiteral(IntegerLiteral node) => js.number(node.value);
2053 2046
2054 @override 2047 @override
2055 visitDoubleLiteral(DoubleLiteral node) => js.number(node.value); 2048 visitDoubleLiteral(DoubleLiteral node) => js.number(node.value);
2056 2049
2057 @override 2050 @override
2058 visitNullLiteral(NullLiteral node) => new JS.LiteralNull(); 2051 visitNullLiteral(NullLiteral node) => new JS.LiteralNull();
2059 2052
2060 @override 2053 @override
2061 visitListLiteral(ListLiteral node) { 2054 visitListLiteral(ListLiteral node) {
2062 // TODO(jmesserly): make this faster. We're wasting an array. 2055 JS.Expression list = new JS.ArrayInitializer(_visitList(node.elements));
2063 var list = js.call('new #.from(#)', [ 2056
2064 _emitTypeName(node.staticType), 2057 ParameterizedType type = node.staticType;
2065 new JS.ArrayInitializer(_visitList(node.elements)) 2058 if (type.typeArguments.any((a) => a != types.dynamicType)) {
2066 ]); 2059 list = js.call('dart.setType(#, #)', [list, _emitTypeName(type)]);
2060 }
2067 if (node.constKeyword != null) { 2061 if (node.constKeyword != null) {
2068 list = js.commentExpression('Unimplemented const', list); 2062 list = js.commentExpression('Unimplemented const', list);
2069 } 2063 }
2070 return list; 2064 return list;
2071 } 2065 }
2072 2066
2073 @override 2067 @override
2074 visitMapLiteral(MapLiteral node) { 2068 visitMapLiteral(MapLiteral node) {
2069 // TODO(jmesserly): we can likely make these faster.
2075 var entries = node.entries; 2070 var entries = node.entries;
2076 var mapArguments = null; 2071 var mapArguments = null;
2077 if (entries.isEmpty) return js.call('dart.map()'); 2072 if (entries.isEmpty) {
2078 2073 mapArguments = [];
2079 // Use JS object literal notation if possible, otherwise use an array. 2074 } else if (entries.every((e) => e.key is StringLiteral)) {
2080 // We could do this any time all keys are non-nullable String type. 2075 // Use JS object literal notation if possible, otherwise use an array.
2081 // For now, support StringLiteral as the common non-nullable String case. 2076 // We could do this any time all keys are non-nullable String type.
2082 if (entries.every((e) => e.key is StringLiteral)) { 2077 // For now, support StringLiteral as the common non-nullable String case.
2083 var props = []; 2078 var props = [];
2084 for (var e in entries) { 2079 for (var e in entries) {
2085 props.add(new JS.Property(_visit(e.key), _visit(e.value))); 2080 props.add(new JS.Property(_visit(e.key), _visit(e.value)));
2086 } 2081 }
2087 mapArguments = new JS.ObjectInitializer(props); 2082 mapArguments = new JS.ObjectInitializer(props);
2088 } else { 2083 } else {
2089 var values = []; 2084 var values = [];
2090 for (var e in entries) { 2085 for (var e in entries) {
2091 values.add(_visit(e.key)); 2086 values.add(_visit(e.key));
2092 values.add(_visit(e.value)); 2087 values.add(_visit(e.value));
2093 } 2088 }
2094 mapArguments = new JS.ArrayInitializer(values); 2089 mapArguments = new JS.ArrayInitializer(values);
2095 } 2090 }
2096 return js.call('dart.map(#)', [mapArguments]); 2091 // TODO(jmesserly): add generic types args.
2092 var map = js.call('dart.map(#)', [mapArguments]);
2093 if (node.constKeyword != null) {
2094 map = js.commentExpression('Unimplemented const', map);
2095 }
2096 return map;
2097 } 2097 }
2098 2098
2099 @override 2099 @override
2100 JS.LiteralString visitSimpleStringLiteral(SimpleStringLiteral node) => 2100 JS.LiteralString visitSimpleStringLiteral(SimpleStringLiteral node) =>
2101 js.escapedString(node.value, node.isSingleQuoted ? "'" : '"'); 2101 js.escapedString(node.value, node.isSingleQuoted ? "'" : '"');
2102 2102
2103 @override 2103 @override
2104 JS.Expression visitAdjacentStrings(AdjacentStrings node) => 2104 JS.Expression visitAdjacentStrings(AdjacentStrings node) =>
2105 _visitListToBinary(node.strings, '+'); 2105 _visitListToBinary(node.strings, '+');
2106 2106
(...skipping 279 matching lines...) Expand 10 before | Expand all | Expand 10 after
2386 return filepath; 2386 return filepath;
2387 } 2387 }
2388 2388
2389 // TODO(jmesserly): validate the library. See issue #135. 2389 // TODO(jmesserly): validate the library. See issue #135.
2390 bool _isJsNameAnnotation(DartObjectImpl value) => value.type.name == 'JsName'; 2390 bool _isJsNameAnnotation(DartObjectImpl value) => value.type.name == 'JsName';
2391 2391
2392 // TODO(jacobr): we would like to do something like the following 2392 // TODO(jacobr): we would like to do something like the following
2393 // but we don't have summary support yet. 2393 // but we don't have summary support yet.
2394 // bool _supportJsExtensionMethod(AnnotatedNode node) => 2394 // bool _supportJsExtensionMethod(AnnotatedNode node) =>
2395 // _getAnnotation(node, "SupportJsExtensionMethod") != null; 2395 // _getAnnotation(node, "SupportJsExtensionMethod") != null;
OLDNEW
« no previous file with comments | « lib/runtime/dart_runtime.js ('k') | lib/src/dependency_graph.dart » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698