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 |
ahe
2012/11/14 13:51:30
All my comments in this file are nitpicking.
| |
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 dart2js; | 5 part of dart2js; |
6 | 6 |
7 /** | 7 /** |
8 * If true, print a warning for each method that was resolved, but not | 8 * If true, print a warning for each method that was resolved, but not |
9 * compiled. | 9 * compiled. |
10 */ | 10 */ |
11 const bool REPORT_EXCESS_RESOLUTION = false; | 11 const bool REPORT_EXCESS_RESOLUTION = false; |
(...skipping 55 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
67 : this.constantSystem = constantSystem; | 67 : this.constantSystem = constantSystem; |
68 | 68 |
69 void enqueueAllTopLevelFunctions(LibraryElement lib, Enqueuer world) { | 69 void enqueueAllTopLevelFunctions(LibraryElement lib, Enqueuer world) { |
70 lib.forEachExport((Element e) { | 70 lib.forEachExport((Element e) { |
71 if (e.isFunction()) world.addToWorkList(e); | 71 if (e.isFunction()) world.addToWorkList(e); |
72 }); | 72 }); |
73 } | 73 } |
74 | 74 |
75 void enqueueHelpers(Enqueuer world); | 75 void enqueueHelpers(Enqueuer world); |
76 void codegen(WorkItem work); | 76 void codegen(WorkItem work); |
77 void processNativeClasses(Enqueuer world, | 77 |
78 Collection<LibraryElement> libraries); | 78 // The backend determines the native resolution enqueuer so tools like |
79 // dart2dart can ignore the native classes. | |
80 native.NativeEnqueuer nativeResolutionEnqueuer(world, bool liveTypeAnalysis) = > | |
ahe
2012/11/14 13:51:30
Long line. As a matter of style, I prefer to avoi
ahe
2012/11/14 13:51:30
I don't think the option liveTypeAnalysis is neces
ahe
2012/11/14 13:51:30
An undocumented property of the library native_han
ngeoffray
2012/11/14 21:17:39
Line too long, and the style we used is not to use
sra1
2012/11/15 00:09:10
Almost all the functionality in here will be neede
sra1
2012/11/15 00:09:10
Done.
sra1
2012/11/15 00:09:10
Done.
sra1
2012/11/15 00:09:10
I see plenty of examples.
| |
81 new native.NativeEnqueuer(); | |
82 native.NativeEnqueuer nativeCodegenEnqueuer(world, bool liveTypeAnalysis) => | |
83 new native.NativeEnqueuer(); | |
84 | |
79 void assembleProgram(); | 85 void assembleProgram(); |
80 List<CompilerTask> get tasks; | 86 List<CompilerTask> get tasks; |
81 | 87 |
82 // TODO(ahe,karlklose): rename this? | 88 // TODO(ahe,karlklose): rename this? |
83 void dumpInferredTypes() {} | 89 void dumpInferredTypes() {} |
84 | 90 |
85 ItemCompilationContext createItemCompilationContext() { | 91 ItemCompilationContext createItemCompilationContext() { |
86 return new ItemCompilationContext(); | 92 return new ItemCompilationContext(); |
87 } | 93 } |
88 | 94 |
89 SourceString getCheckedModeHelper(DartType type) => null; | 95 SourceString getCheckedModeHelper(DartType type) => null; |
90 void registerInstantiatedClass(ClassElement cls, Enqueuer enqueuer) {} | 96 void registerInstantiatedClass(ClassElement cls, Enqueuer enqueuer) {} |
91 | 97 |
92 Element getInterceptor(Selector selector); | 98 Element getInterceptor(Selector selector); |
93 } | 99 } |
94 | 100 |
95 abstract class Compiler implements DiagnosticListener { | 101 abstract class Compiler implements DiagnosticListener { |
96 final Map<String, LibraryElement> libraries; | 102 final Map<String, LibraryElement> libraries; |
97 int nextFreeClassId = 0; | 103 int nextFreeClassId = 0; |
98 World world; | 104 World world; |
99 String assembledCode; | 105 String assembledCode; |
100 Types types; | 106 Types types; |
101 | 107 |
102 final bool enableMinification; | 108 final bool enableMinification; |
103 final bool enableTypeAssertions; | 109 final bool enableTypeAssertions; |
104 final bool enableUserAssertions; | 110 final bool enableUserAssertions; |
105 final bool enableConcreteTypeInference; | 111 final bool enableConcreteTypeInference; |
112 final bool enableNativeLiveTypeAnalysis; | |
106 | 113 |
107 bool disableInlining = false; | 114 bool disableInlining = false; |
108 | 115 |
109 final Tracer tracer; | 116 final Tracer tracer; |
110 | 117 |
111 CompilerTask measuredTask; | 118 CompilerTask measuredTask; |
112 Element _currentElement; | 119 Element _currentElement; |
113 LibraryElement coreLibrary; | 120 LibraryElement coreLibrary; |
114 LibraryElement isolateLibrary; | 121 LibraryElement isolateLibrary; |
115 LibraryElement jsHelperLibrary; | 122 LibraryElement jsHelperLibrary; |
(...skipping 87 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
203 | 210 |
204 bool compilationFailed = false; | 211 bool compilationFailed = false; |
205 | 212 |
206 bool hasCrashed = false; | 213 bool hasCrashed = false; |
207 | 214 |
208 Compiler({this.tracer: const Tracer(), | 215 Compiler({this.tracer: const Tracer(), |
209 this.enableTypeAssertions: false, | 216 this.enableTypeAssertions: false, |
210 this.enableUserAssertions: false, | 217 this.enableUserAssertions: false, |
211 this.enableConcreteTypeInference: false, | 218 this.enableConcreteTypeInference: false, |
212 this.enableMinification: false, | 219 this.enableMinification: false, |
220 this.enableNativeLiveTypeAnalysis: false, | |
213 bool emitJavaScript: true, | 221 bool emitJavaScript: true, |
214 bool generateSourceMap: true, | 222 bool generateSourceMap: true, |
215 bool disallowUnsafeEval: false, | 223 bool disallowUnsafeEval: false, |
216 List<String> strips: const []}) | 224 List<String> strips: const []}) |
217 : libraries = new Map<String, LibraryElement>(), | 225 : libraries = new Map<String, LibraryElement>(), |
218 progress = new Stopwatch() { | 226 progress = new Stopwatch() { |
219 progress.start(); | 227 progress.start(); |
220 world = new World(this); | 228 world = new World(this); |
221 scanner = new ScannerTask(this); | 229 scanner = new ScannerTask(this); |
222 dietParser = new DietParserTask(this); | 230 dietParser = new DietParserTask(this); |
(...skipping 285 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
508 reportFatalError('Could not find $MAIN', mainApp); | 516 reportFatalError('Could not find $MAIN', mainApp); |
509 } else { | 517 } else { |
510 if (!main.isFunction()) reportFatalError('main is not a function', main); | 518 if (!main.isFunction()) reportFatalError('main is not a function', main); |
511 FunctionElement mainMethod = main; | 519 FunctionElement mainMethod = main; |
512 FunctionSignature parameters = mainMethod.computeSignature(this); | 520 FunctionSignature parameters = mainMethod.computeSignature(this); |
513 parameters.forEachParameter((Element parameter) { | 521 parameters.forEachParameter((Element parameter) { |
514 reportFatalError('main cannot have parameters', parameter); | 522 reportFatalError('main cannot have parameters', parameter); |
515 }); | 523 }); |
516 } | 524 } |
517 | 525 |
526 enqueuer.resolution.nativeEnqueuer = | |
527 backend.nativeResolutionEnqueuer(enqueuer.resolution, | |
528 enableNativeLiveTypeAnalysis); | |
529 enqueuer.codegen.nativeEnqueuer = | |
530 backend.nativeCodegenEnqueuer(enqueuer.codegen, | |
531 enableNativeLiveTypeAnalysis); | |
532 | |
518 log('Resolving...'); | 533 log('Resolving...'); |
519 phase = PHASE_RESOLVING; | 534 phase = PHASE_RESOLVING; |
520 backend.enqueueHelpers(enqueuer.resolution); | 535 backend.enqueueHelpers(enqueuer.resolution); |
521 processQueue(enqueuer.resolution, main); | 536 processQueue(enqueuer.resolution, main); |
522 log('Resolved ${enqueuer.resolution.resolvedElements.length} elements.'); | 537 log('Resolved ${enqueuer.resolution.resolvedElements.length} elements.'); |
538 enqueuer.resolution.nativeEnqueuer.logSummary(log); | |
ahe
2012/11/14 13:51:30
I like this approach. How about merging these two
sra1
2012/11/15 00:09:10
Done.
| |
523 | 539 |
524 if (compilationFailed) return; | 540 if (compilationFailed) return; |
525 | 541 |
526 log('Inferring types...'); | 542 log('Inferring types...'); |
527 typesTask.onResolutionComplete(main); | 543 typesTask.onResolutionComplete(main); |
528 | 544 |
529 // TODO(ahe): Remove this line. Eventually, enqueuer.resolution | 545 // TODO(ahe): Remove this line. Eventually, enqueuer.resolution |
530 // should know this. | 546 // should know this. |
531 world.populate(); | 547 world.populate(); |
532 | 548 |
533 log('Compiling...'); | 549 log('Compiling...'); |
534 phase = PHASE_COMPILING; | 550 phase = PHASE_COMPILING; |
535 processQueue(enqueuer.codegen, main); | 551 processQueue(enqueuer.codegen, main); |
536 log('Compiled ${codegenWorld.generatedCode.length} methods.'); | 552 log('Compiled ${codegenWorld.generatedCode.length} methods.'); |
553 enqueuer.codegen.nativeEnqueuer.logSummary(log); | |
ahe
2012/11/14 13:51:30
Ditto.
sra1
2012/11/15 00:09:10
Done.
| |
537 | 554 |
538 if (compilationFailed) return; | 555 if (compilationFailed) return; |
539 | 556 |
540 backend.assembleProgram(); | 557 backend.assembleProgram(); |
541 | 558 |
542 checkQueues(); | 559 checkQueues(); |
543 } | 560 } |
544 | 561 |
545 void processQueue(Enqueuer world, Element main) { | 562 void processQueue(Enqueuer world, Element main) { |
546 backend.processNativeClasses(world, libraries.values); | 563 world.nativeEnqueuer.processNativeClasses(libraries.values); |
547 world.addToWorkList(main); | 564 world.addToWorkList(main); |
548 progress.reset(); | 565 progress.reset(); |
549 world.forEach((WorkItem work) { | 566 world.forEach((WorkItem work) { |
550 withCurrentElement(work.element, () => work.run(this, world)); | 567 withCurrentElement(work.element, () => work.run(this, world)); |
551 }); | 568 }); |
552 world.queueIsClosed = true; | 569 world.queueIsClosed = true; |
553 if (compilationFailed) return; | 570 if (compilationFailed) return; |
554 assert(world.checkNoEnqueuedInvokedInstanceMethods()); | 571 assert(world.checkNoEnqueuedInvokedInstanceMethods()); |
555 if (DUMP_INFERRED_TYPES && phase == PHASE_COMPILING) { | 572 if (DUMP_INFERRED_TYPES && phase == PHASE_COMPILING) { |
556 backend.dumpInferredTypes(); | 573 backend.dumpInferredTypes(); |
(...skipping 82 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
639 if (phase == PHASE_RESOLVING) { | 656 if (phase == PHASE_RESOLVING) { |
640 log('Resolved ${enqueuer.resolution.resolvedElements.length} ' | 657 log('Resolved ${enqueuer.resolution.resolvedElements.length} ' |
641 'elements.'); | 658 'elements.'); |
642 progress.reset(); | 659 progress.reset(); |
643 } | 660 } |
644 } | 661 } |
645 Element element = work.element; | 662 Element element = work.element; |
646 TreeElements result = world.getCachedElements(element); | 663 TreeElements result = world.getCachedElements(element); |
647 if (result != null) return result; | 664 if (result != null) return result; |
648 if (!identical(world, enqueuer.resolution)) { | 665 if (!identical(world, enqueuer.resolution)) { |
666 throw 'Internal error: unresolved element: $element.'; | |
ahe
2012/11/14 13:51:30
Remove this. FYI: you can often use --throw-on-er
ngeoffray
2012/11/14 21:17:39
Remove debugging code.
sra1
2012/11/15 00:09:10
Done.
| |
649 internalErrorOnElement(element, | 667 internalErrorOnElement(element, |
650 'Internal error: unresolved element: $element.'); | 668 'Internal error: unresolved element: $element.'); |
651 } | 669 } |
652 result = analyzeElement(element); | 670 result = analyzeElement(element); |
653 assert(invariant(element, element.isDeclaration)); | 671 assert(invariant(element, element.isDeclaration)); |
654 enqueuer.resolution.resolvedElements[element] = result; | 672 enqueuer.resolution.resolvedElements[element] = result; |
655 return result; | 673 return result; |
656 } | 674 } |
657 | 675 |
658 void codegen(WorkItem work, Enqueuer world) { | 676 void codegen(WorkItem work, Enqueuer world) { |
(...skipping 244 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
903 // TODO(johnniwinther): Use [spannable] and [message] to provide better | 921 // TODO(johnniwinther): Use [spannable] and [message] to provide better |
904 // information on assertion errors. | 922 // information on assertion errors. |
905 if (condition is Function){ | 923 if (condition is Function){ |
906 condition = condition(); | 924 condition = condition(); |
907 } | 925 } |
908 if (spannable == null || !condition) { | 926 if (spannable == null || !condition) { |
909 throw new SpannableAssertionFailure(spannable, message); | 927 throw new SpannableAssertionFailure(spannable, message); |
910 } | 928 } |
911 return true; | 929 return true; |
912 } | 930 } |
OLD | NEW |