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 /** | 5 /** |
| 6 * A function element that represents a closure call. The signature is copied | 6 * A function element that represents a closure call. The signature is copied |
| 7 * from the given element. | 7 * from the given element. |
| 8 */ | 8 */ |
| 9 class ClosureInvocationElement extends FunctionElement { | 9 class ClosureInvocationElement extends FunctionElement { |
| 10 ClosureInvocationElement(SourceString name, | 10 ClosureInvocationElement(SourceString name, |
| (...skipping 17 matching lines...) Expand all Loading... | |
| 28 NativeEmitter nativeEmitter; | 28 NativeEmitter nativeEmitter; |
| 29 StringBuffer boundClosureBuffer; | 29 StringBuffer boundClosureBuffer; |
| 30 StringBuffer mainBuffer; | 30 StringBuffer mainBuffer; |
| 31 /** Shorter access to [isolatePropertiesName]. Both here in the code, as | 31 /** Shorter access to [isolatePropertiesName]. Both here in the code, as |
| 32 well as in the generated code. */ | 32 well as in the generated code. */ |
| 33 String isolateProperties; | 33 String isolateProperties; |
| 34 String classesCollector; | 34 String classesCollector; |
| 35 final Map<int, String> boundClosureCache; | 35 final Map<int, String> boundClosureCache; |
| 36 | 36 |
| 37 final bool generateSourceMap; | 37 final bool generateSourceMap; |
| 38 final List<SourceMappingEntry> sourceMappings; | 38 final SourceMapBuilder sourceMapBuilder; |
| 39 | 39 |
| 40 CodeEmitterTask(Compiler compiler, [bool generateSourceMap = false]) | 40 CodeEmitterTask(Compiler compiler, [bool generateSourceMap = false]) |
| 41 : namer = compiler.namer, | 41 : namer = compiler.namer, |
| 42 boundClosureBuffer = new StringBuffer(), | 42 boundClosureBuffer = new StringBuffer(), |
| 43 mainBuffer = new StringBuffer(), | 43 mainBuffer = new StringBuffer(), |
| 44 boundClosureCache = new Map<int, String>(), | 44 boundClosureCache = new Map<int, String>(), |
| 45 generateSourceMap = generateSourceMap, | 45 generateSourceMap = generateSourceMap, |
| 46 sourceMappings = new List<SourceMappingEntry>(), | 46 sourceMapBuilder = new SourceMapBuilder(), |
| 47 super(compiler) { | 47 super(compiler) { |
| 48 nativeEmitter = new NativeEmitter(this); | 48 nativeEmitter = new NativeEmitter(this); |
| 49 } | 49 } |
| 50 | 50 |
| 51 String get name() => 'CodeEmitter'; | 51 String get name() => 'CodeEmitter'; |
| 52 | 52 |
| 53 String get defineClassName() | 53 String get defineClassName() |
| 54 => '${namer.ISOLATE}.\$defineClass'; | 54 => '${namer.ISOLATE}.\$defineClass'; |
| 55 String get finishClassesName() | 55 String get finishClassesName() |
| 56 => '${namer.ISOLATE}.\$finishClasses'; | 56 => '${namer.ISOLATE}.\$finishClasses'; |
| (...skipping 191 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 248 buffer.add("$name = $value;\n"); | 248 buffer.add("$name = $value;\n"); |
| 249 } | 249 } |
| 250 | 250 |
| 251 void emitFinishIsolateConstructorInvocation(StringBuffer buffer) { | 251 void emitFinishIsolateConstructorInvocation(StringBuffer buffer) { |
| 252 String isolate = namer.ISOLATE; | 252 String isolate = namer.ISOLATE; |
| 253 buffer.add("$isolate = $finishIsolateConstructorName($isolate);\n"); | 253 buffer.add("$isolate = $finishIsolateConstructorName($isolate);\n"); |
| 254 } | 254 } |
| 255 | 255 |
| 256 void addParameterStub(FunctionElement member, | 256 void addParameterStub(FunctionElement member, |
| 257 Selector selector, | 257 Selector selector, |
| 258 void defineInstanceMember(String invocationName, | 258 DefineInstanceMember defineInstanceMember) { |
| 259 String definition)) { | |
| 260 FunctionSignature parameters = member.computeSignature(compiler); | 259 FunctionSignature parameters = member.computeSignature(compiler); |
| 261 int positionalArgumentCount = selector.positionalArgumentCount; | 260 int positionalArgumentCount = selector.positionalArgumentCount; |
| 262 if (positionalArgumentCount == parameters.parameterCount) { | 261 if (positionalArgumentCount == parameters.parameterCount) { |
| 263 assert(selector.namedArgumentCount == 0); | 262 assert(selector.namedArgumentCount == 0); |
| 264 return; | 263 return; |
| 265 } | 264 } |
| 266 ConstantHandler handler = compiler.constantHandler; | 265 ConstantHandler handler = compiler.constantHandler; |
| 267 List<SourceString> names = selector.getOrderedNamedArguments(); | 266 List<SourceString> names = selector.getOrderedNamedArguments(); |
| 268 | 267 |
| 269 String invocationName = | 268 String invocationName = |
| (...skipping 83 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 353 indexOfLastOptionalArgumentInParameters, buffer); | 352 indexOfLastOptionalArgumentInParameters, buffer); |
| 354 } else { | 353 } else { |
| 355 String arguments = Strings.join(argumentsBuffer, ","); | 354 String arguments = Strings.join(argumentsBuffer, ","); |
| 356 buffer.add(' return this.${namer.getName(member)}($arguments)'); | 355 buffer.add(' return this.${namer.getName(member)}($arguments)'); |
| 357 } | 356 } |
| 358 buffer.add('\n}'); | 357 buffer.add('\n}'); |
| 359 defineInstanceMember(invocationName, buffer.toString()); | 358 defineInstanceMember(invocationName, buffer.toString()); |
| 360 } | 359 } |
| 361 | 360 |
| 362 void addParameterStubs(FunctionElement member, | 361 void addParameterStubs(FunctionElement member, |
| 363 void defineInstanceMember(String invocationName, | 362 DefineInstanceMember defineInstanceMember) { |
| 364 String definition)) { | |
| 365 Set<Selector> selectors = compiler.codegenWorld.invokedNames[member.name]; | 363 Set<Selector> selectors = compiler.codegenWorld.invokedNames[member.name]; |
| 366 if (selectors == null) return; | 364 if (selectors == null) return; |
| 367 for (Selector selector in selectors) { | 365 for (Selector selector in selectors) { |
| 368 if (!selector.applies(member, compiler)) continue; | 366 if (!selector.applies(member, compiler)) continue; |
| 369 addParameterStub(member, selector, defineInstanceMember); | 367 addParameterStub(member, selector, defineInstanceMember); |
| 370 } | 368 } |
| 371 } | 369 } |
| 372 | 370 |
| 373 bool instanceFieldNeedsGetter(Element member) { | 371 bool instanceFieldNeedsGetter(Element member) { |
| 374 assert(member.kind === ElementKind.FIELD); | 372 assert(member.kind === ElementKind.FIELD); |
| 375 return compiler.codegenWorld.hasInvokedGetter(member, compiler); | 373 return compiler.codegenWorld.hasInvokedGetter(member, compiler); |
| 376 } | 374 } |
| 377 | 375 |
| 378 bool instanceFieldNeedsSetter(Element member) { | 376 bool instanceFieldNeedsSetter(Element member) { |
| 379 assert(member.kind === ElementKind.FIELD); | 377 assert(member.kind === ElementKind.FIELD); |
| 380 return (member.modifiers === null || !member.modifiers.isFinal()) | 378 return (member.modifiers === null || !member.modifiers.isFinal()) |
| 381 && compiler.codegenWorld.hasInvokedSetter(member, compiler); | 379 && compiler.codegenWorld.hasInvokedSetter(member, compiler); |
| 382 } | 380 } |
| 383 | 381 |
| 384 String compiledFieldName(Element member) { | 382 String compiledFieldName(Element member) { |
| 385 assert(member.kind === ElementKind.FIELD); | 383 assert(member.kind === ElementKind.FIELD); |
| 386 return member.isNative() | 384 return member.isNative() |
| 387 ? member.name.slowToString() | 385 ? member.name.slowToString() |
| 388 : namer.getName(member); | 386 : namer.getName(member); |
| 389 } | 387 } |
| 390 | 388 |
| 391 void addInstanceMember(Element member, | 389 void addInstanceMember(Element member, |
| 392 void defineInstanceMember(String invocationName, | 390 DefineInstanceMember defineInstanceMember) { |
| 393 String definition)) { | |
| 394 // TODO(floitsch): we don't need to deal with members of | 391 // TODO(floitsch): we don't need to deal with members of |
| 395 // uninstantiated classes, that have been overwritten by subclasses. | 392 // uninstantiated classes, that have been overwritten by subclasses. |
| 396 | 393 |
| 397 if (member.kind === ElementKind.FUNCTION | 394 if (member.kind === ElementKind.FUNCTION |
| 398 || member.kind === ElementKind.GENERATIVE_CONSTRUCTOR_BODY | 395 || member.kind === ElementKind.GENERATIVE_CONSTRUCTOR_BODY |
| 399 || member.kind === ElementKind.GETTER | 396 || member.kind === ElementKind.GETTER |
| 400 || member.kind === ElementKind.SETTER) { | 397 || member.kind === ElementKind.SETTER) { |
| 401 if (member.modifiers !== null && member.modifiers.isAbstract()) return; | 398 if (member.modifiers !== null && member.modifiers.isAbstract()) return; |
| 402 String codeBlock = compiler.codegenWorld.generatedCode[member]; | 399 CodeBlock codeBlock = compiler.codegenWorld.generatedCode[member]; |
| 403 if (codeBlock == null) return; | 400 if (codeBlock == null) return; |
| 404 defineInstanceMember(namer.getName(member), codeBlock); | 401 defineInstanceMember(namer.getName(member), |
| 402 codeBlock.code, | |
| 403 codeBlock.sourceMappings); | |
| 405 codeBlock = compiler.codegenWorld.generatedBailoutCode[member]; | 404 codeBlock = compiler.codegenWorld.generatedBailoutCode[member]; |
| 406 if (codeBlock !== null) { | 405 if (codeBlock !== null) { |
| 407 defineInstanceMember(compiler.namer.getBailoutName(member), codeBlock); | 406 defineInstanceMember(compiler.namer.getBailoutName(member), |
| 407 codeBlock.code, | |
| 408 codeBlock.sourceMappings); | |
| 408 } | 409 } |
| 409 FunctionElement function = member; | 410 FunctionElement function = member; |
| 410 FunctionSignature parameters = function.computeSignature(compiler); | 411 FunctionSignature parameters = function.computeSignature(compiler); |
| 411 if (!parameters.optionalParameters.isEmpty()) { | 412 if (!parameters.optionalParameters.isEmpty()) { |
| 412 addParameterStubs(member, defineInstanceMember); | 413 addParameterStubs(member, defineInstanceMember); |
| 413 } | 414 } |
| 414 } else if (member.kind === ElementKind.FIELD) { | 415 } else if (member.kind === ElementKind.FIELD) { |
| 415 SourceString name = member.name; | 416 SourceString name = member.name; |
| 416 ClassElement cls = member.getEnclosingClass(); | 417 ClassElement cls = member.getEnclosingClass(); |
| 417 if (cls.lookupSuperMember(name) !== null) { | 418 if (cls.lookupSuperMember(name) !== null) { |
| (...skipping 63 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 481 classElement.forEachInstanceField( | 482 classElement.forEachInstanceField( |
| 482 addField, | 483 addField, |
| 483 includeBackendMembers: true, | 484 includeBackendMembers: true, |
| 484 includeSuperMembers: isInstantiated && !classElement.isNative()); | 485 includeSuperMembers: isInstantiated && !classElement.isNative()); |
| 485 } | 486 } |
| 486 | 487 |
| 487 void emitInstanceMembers(ClassElement classElement, | 488 void emitInstanceMembers(ClassElement classElement, |
| 488 StringBuffer buffer, | 489 StringBuffer buffer, |
| 489 bool needsLeadingComma) { | 490 bool needsLeadingComma) { |
| 490 bool needsComma = needsLeadingComma; | 491 bool needsComma = needsLeadingComma; |
| 491 void defineInstanceMember(String name, String value) { | 492 void defineInstanceMember(String name, |
| 493 String value, | |
| 494 [List<SourceMappingEntry> sourceMappings]) { | |
| 492 if (needsComma) buffer.add(','); | 495 if (needsComma) buffer.add(','); |
| 493 needsComma = true; | 496 needsComma = true; |
| 494 buffer.add('\n'); | 497 buffer.add('\n'); |
| 495 buffer.add(' $name: $value'); | 498 buffer.add(' $name: '); |
| 499 sourceMapBuilder.addCodeBlock(sourceMappings, buffer.length); | |
| 500 buffer.add('$value'); | |
| 496 } | 501 } |
| 497 | 502 |
| 498 classElement.forEachMember(includeBackendMembers: true, | 503 classElement.forEachMember(includeBackendMembers: true, |
| 499 f: (ClassElement enclosing, Element member) { | 504 f: (ClassElement enclosing, Element member) { |
| 500 if (member.isInstanceMember()) { | 505 if (member.isInstanceMember()) { |
| 501 addInstanceMember(member, defineInstanceMember); | 506 addInstanceMember(member, defineInstanceMember); |
| 502 } | 507 } |
| 503 }); | 508 }); |
| 504 | 509 |
| 505 generateTypeTests(classElement, (Element other) { | 510 generateTypeTests(classElement, (Element other) { |
| (...skipping 103 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 609 | 614 |
| 610 void emitFinishClassesInvocationIfNecessary(StringBuffer buffer) { | 615 void emitFinishClassesInvocationIfNecessary(StringBuffer buffer) { |
| 611 if (needsDefineClass) { | 616 if (needsDefineClass) { |
| 612 buffer.add("$finishClassesName($classesCollector);\n"); | 617 buffer.add("$finishClassesName($classesCollector);\n"); |
| 613 // Reset the map. | 618 // Reset the map. |
| 614 buffer.add("$classesCollector = {};\n"); | 619 buffer.add("$classesCollector = {};\n"); |
| 615 } | 620 } |
| 616 } | 621 } |
| 617 | 622 |
| 618 void emitStaticFunctionsWithNamer(StringBuffer buffer, | 623 void emitStaticFunctionsWithNamer(StringBuffer buffer, |
| 619 Map<Element, String> generatedCode, | 624 Map<Element, CodeBlock> generatedCode, |
| 620 String functionNamer(Element element)) { | 625 String functionNamer(Element element)) { |
| 621 generatedCode.forEach((Element element, String codeBlock) { | 626 generatedCode.forEach((Element element, CodeBlock codeBlock) { |
| 622 if (!element.isInstanceMember()) { | 627 if (!element.isInstanceMember()) { |
| 623 String functionName = functionNamer(element); | 628 String functionName = functionNamer(element); |
| 624 buffer.add('$isolateProperties.$functionName = '); | 629 buffer.add('$isolateProperties.$functionName = '); |
| 625 int beginPosition = buffer.length; | 630 sourceMapBuilder.addCodeBlock(codeBlock.sourceMappings, buffer.length); |
| 626 buffer.add(codeBlock); | 631 buffer.add('${codeBlock.code};\n\n'); |
| 627 int endPosition = buffer.length; | |
| 628 buffer.add(';\n\n'); | |
| 629 if (generateSourceMap) { | |
| 630 addSourceMapping(element, beginPosition, endPosition); | |
| 631 } | |
| 632 } | 632 } |
| 633 }); | 633 }); |
| 634 } | 634 } |
| 635 | 635 |
| 636 void emitStaticFunctions(StringBuffer buffer) { | 636 void emitStaticFunctions(StringBuffer buffer) { |
| 637 emitStaticFunctionsWithNamer(buffer, | 637 emitStaticFunctionsWithNamer(buffer, |
| 638 compiler.codegenWorld.generatedCode, | 638 compiler.codegenWorld.generatedCode, |
| 639 namer.getName); | 639 namer.getName); |
| 640 emitStaticFunctionsWithNamer(buffer, | 640 emitStaticFunctionsWithNamer(buffer, |
| 641 compiler.codegenWorld.generatedBailoutCode, | 641 compiler.codegenWorld.generatedBailoutCode, |
| (...skipping 10 matching lines...) Expand all Loading... | |
| 652 // Note: the callElement will not have any enclosingElement. | 652 // Note: the callElement will not have any enclosingElement. |
| 653 FunctionElement callElement = | 653 FunctionElement callElement = |
| 654 new ClosureInvocationElement(namer.CLOSURE_INVOCATION_NAME, element); | 654 new ClosureInvocationElement(namer.CLOSURE_INVOCATION_NAME, element); |
| 655 String staticName = namer.getName(element); | 655 String staticName = namer.getName(element); |
| 656 int parameterCount = element.parameterCount(compiler); | 656 int parameterCount = element.parameterCount(compiler); |
| 657 String invocationName = | 657 String invocationName = |
| 658 namer.instanceMethodName(element.getLibrary(), callElement.name, | 658 namer.instanceMethodName(element.getLibrary(), callElement.name, |
| 659 parameterCount); | 659 parameterCount); |
| 660 String fieldAccess = '$isolateProperties.$staticName'; | 660 String fieldAccess = '$isolateProperties.$staticName'; |
| 661 buffer.add("$fieldAccess.$invocationName = $fieldAccess;\n"); | 661 buffer.add("$fieldAccess.$invocationName = $fieldAccess;\n"); |
| 662 addParameterStubs(callElement, (String name, String value) { | 662 addParameterStubs(callElement, ( |
| 663 String name, String value, | |
| 664 [List<SourceMappingEntry> sourceMappings]) { | |
| 663 buffer.add('$fieldAccess.$name = $value;\n'); | 665 buffer.add('$fieldAccess.$name = $value;\n'); |
| 664 }); | 666 }); |
| 665 // If a static function is used as a closure we need to add its name | 667 // If a static function is used as a closure we need to add its name |
| 666 // in case it is used in spawnFunction. | 668 // in case it is used in spawnFunction. |
| 667 String fieldName = namer.STATIC_CLOSURE_NAME_NAME; | 669 String fieldName = namer.STATIC_CLOSURE_NAME_NAME; |
| 668 buffer.add('$fieldAccess.$fieldName = "$staticName";\n'); | 670 buffer.add('$fieldAccess.$fieldName = "$staticName";\n'); |
| 669 } | 671 } |
| 670 } | 672 } |
| 671 | 673 |
| 672 void emitDynamicFunctionGetter(FunctionElement member, | 674 void emitDynamicFunctionGetter(FunctionElement member, |
| 673 defineInstanceMember(String invocationName, | 675 DefineInstanceMember defineInstanceMember) { |
| 674 String definition)) { | |
| 675 // For every method that has the same name as a property-get we create a | 676 // For every method that has the same name as a property-get we create a |
| 676 // getter that returns a bound closure. Say we have a class 'A' with method | 677 // getter that returns a bound closure. Say we have a class 'A' with method |
| 677 // 'foo' and somewhere in the code there is a dynamic property get of | 678 // 'foo' and somewhere in the code there is a dynamic property get of |
| 678 // 'foo'. Then we generate the following code (in pseudo Dart/JavaScript): | 679 // 'foo'. Then we generate the following code (in pseudo Dart/JavaScript): |
| 679 // | 680 // |
| 680 // class A { | 681 // class A { |
| 681 // foo(x, y, z) { ... } // Original function. | 682 // foo(x, y, z) { ... } // Original function. |
| 682 // get foo() { return new BoundClosure499(this, "foo"); } | 683 // get foo() { return new BoundClosure499(this, "foo"); } |
| 683 // } | 684 // } |
| 684 // class BoundClosure499 extends Closure { | 685 // class BoundClosure499 extends Closure { |
| (...skipping 64 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 749 String getterName = namer.getterName(member.getLibrary(), member.name); | 750 String getterName = namer.getterName(member.getLibrary(), member.name); |
| 750 String targetName = namer.instanceMethodName(member.getLibrary(), | 751 String targetName = namer.instanceMethodName(member.getLibrary(), |
| 751 member.name, parameterCount); | 752 member.name, parameterCount); |
| 752 defineInstanceMember( | 753 defineInstanceMember( |
| 753 getterName, | 754 getterName, |
| 754 "function() { return new $closureClass(this, '$targetName'); }"); | 755 "function() { return new $closureClass(this, '$targetName'); }"); |
| 755 } | 756 } |
| 756 | 757 |
| 757 void emitCallStubForGetter(Element member, | 758 void emitCallStubForGetter(Element member, |
| 758 Set<Selector> selectors, | 759 Set<Selector> selectors, |
| 759 void defineInstanceMember(String invocationName, | 760 DefineInstanceMember defineInstanceMember) { |
| 760 String definition)) { | |
| 761 String getter; | 761 String getter; |
| 762 if (member.kind == ElementKind.GETTER) { | 762 if (member.kind == ElementKind.GETTER) { |
| 763 getter = "this.${namer.getterName(member.getLibrary(), member.name)}()"; | 763 getter = "this.${namer.getterName(member.getLibrary(), member.name)}()"; |
| 764 } else { | 764 } else { |
| 765 String name = namer.instanceFieldName(member.getEnclosingClass(), | 765 String name = namer.instanceFieldName(member.getEnclosingClass(), |
| 766 member.name); | 766 member.name); |
| 767 getter = "this.$name"; | 767 getter = "this.$name"; |
| 768 } | 768 } |
| 769 for (Selector selector in selectors) { | 769 for (Selector selector in selectors) { |
| 770 if (selector.applies(member, compiler)) { | 770 if (selector.applies(member, compiler)) { |
| (...skipping 53 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 824 buffer.add(namer.ISOLATE); | 824 buffer.add(namer.ISOLATE); |
| 825 buffer.add(@'''.makeConstantList = function(list) { | 825 buffer.add(@'''.makeConstantList = function(list) { |
| 826 list.immutable$list = true; | 826 list.immutable$list = true; |
| 827 list.fixed$length = true; | 827 list.fixed$length = true; |
| 828 return list; | 828 return list; |
| 829 }; | 829 }; |
| 830 '''); | 830 '''); |
| 831 } | 831 } |
| 832 | 832 |
| 833 void emitExtraAccessors(Element member, | 833 void emitExtraAccessors(Element member, |
| 834 void defineInstanceMember(String invocationName, | 834 DefineInstanceMember defineInstanceMember) { |
| 835 String definition)) { | |
| 836 if (member.kind == ElementKind.GETTER || member.kind == ElementKind.FIELD) { | 835 if (member.kind == ElementKind.GETTER || member.kind == ElementKind.FIELD) { |
| 837 Set<Selector> selectors = compiler.codegenWorld.invokedNames[member.name]; | 836 Set<Selector> selectors = compiler.codegenWorld.invokedNames[member.name]; |
| 838 if (selectors !== null && !selectors.isEmpty()) { | 837 if (selectors !== null && !selectors.isEmpty()) { |
| 839 emitCallStubForGetter(member, selectors, defineInstanceMember); | 838 emitCallStubForGetter(member, selectors, defineInstanceMember); |
| 840 } | 839 } |
| 841 } else if (member.kind == ElementKind.FUNCTION) { | 840 } else if (member.kind == ElementKind.FUNCTION) { |
| 842 if (compiler.codegenWorld.hasInvokedGetter(member, compiler)) { | 841 if (compiler.codegenWorld.hasInvokedGetter(member, compiler)) { |
| 843 emitDynamicFunctionGetter(member, defineInstanceMember); | 842 emitDynamicFunctionGetter(member, defineInstanceMember); |
| 844 } | 843 } |
| 845 } | 844 } |
| 846 } | 845 } |
| 847 | 846 |
| 848 void emitNoSuchMethodCalls(void defineInstanceMember(String invocationName, | 847 void emitNoSuchMethodCalls(DefineInstanceMember defineInstanceMember) { |
| 849 String definition)) { | |
| 850 // Do not generate no such method calls if there is no class. | 848 // Do not generate no such method calls if there is no class. |
| 851 if (compiler.codegenWorld.instantiatedClasses.isEmpty()) return; | 849 if (compiler.codegenWorld.instantiatedClasses.isEmpty()) return; |
| 852 | 850 |
| 853 ClassElement objectClass = | 851 ClassElement objectClass = |
| 854 compiler.coreLibrary.find(const SourceString('Object')); | 852 compiler.coreLibrary.find(const SourceString('Object')); |
| 855 String runtimeObjectPrototype = | 853 String runtimeObjectPrototype = |
| 856 '${namer.isolateAccess(objectClass)}.prototype'; | 854 '${namer.isolateAccess(objectClass)}.prototype'; |
| 857 String noSuchMethodName = | 855 String noSuchMethodName = |
| 858 namer.instanceMethodName(null, Compiler.NO_SUCH_METHOD, 2); | 856 namer.instanceMethodName(null, Compiler.NO_SUCH_METHOD, 2); |
| 859 Collection<LibraryElement> libraries = compiler.libraries.getValues(); | 857 Collection<LibraryElement> libraries = compiler.libraries.getValues(); |
| (...skipping 180 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 1040 emitMain(mainBuffer); | 1038 emitMain(mainBuffer); |
| 1041 mainBuffer.add('function init() {\n'); | 1039 mainBuffer.add('function init() {\n'); |
| 1042 mainBuffer.add(' $isolateProperties = {};\n'); | 1040 mainBuffer.add(' $isolateProperties = {};\n'); |
| 1043 addDefineClassAndFinishClassFunctionsIfNecessary(mainBuffer); | 1041 addDefineClassAndFinishClassFunctionsIfNecessary(mainBuffer); |
| 1044 emitFinishIsolateConstructor(mainBuffer); | 1042 emitFinishIsolateConstructor(mainBuffer); |
| 1045 mainBuffer.add('}\n'); | 1043 mainBuffer.add('}\n'); |
| 1046 compiler.assembledCode = mainBuffer.toString(); | 1044 compiler.assembledCode = mainBuffer.toString(); |
| 1047 | 1045 |
| 1048 if (generateSourceMap) { | 1046 if (generateSourceMap) { |
| 1049 SourceFile compiledFile = new SourceFile(null, compiler.assembledCode); | 1047 SourceFile compiledFile = new SourceFile(null, compiler.assembledCode); |
| 1050 String sourceMap = new SourceMapBuilder().build(sourceMappings, | 1048 String sourceMap = sourceMapBuilder.build(compiledFile); |
| 1051 compiledFile); | |
| 1052 // TODO(podivilov): We should find a better way to return source maps to | 1049 // TODO(podivilov): We should find a better way to return source maps to |
| 1053 // compiler. Using diagnostic handler for that purpose is a temporary | 1050 // compiler. Using diagnostic handler for that purpose is a temporary |
| 1054 // hack. | 1051 // hack. |
| 1055 compiler.reportDiagnostic( | 1052 compiler.reportDiagnostic( |
| 1056 null, sourceMap, new api.Diagnostic(-1, 'source map')); | 1053 null, sourceMap, new api.Diagnostic(-1, 'source map')); |
| 1057 } | 1054 } |
| 1058 }); | 1055 }); |
| 1059 return compiler.assembledCode; | 1056 return compiler.assembledCode; |
| 1060 } | 1057 } |
| 1058 } | |
| 1061 | 1059 |
| 1062 void addSourceMapping(FunctionElement element, | 1060 typedef void DefineInstanceMember(String invocationName, |
|
floitsch
2012/07/02 15:18:32
DefineInstanceMemberFunction ?
imho it reads stran
podivilov
2012/07/03 13:08:49
Done.
| |
| 1063 int beginPosition, | 1061 String definition, |
| 1064 int endPosition) { | 1062 [List<SourceMappingEntry> sourceMappings]); |
| 1065 SourceFile sourceFile = element.getCompilationUnit().script.file; | |
| 1066 FunctionExpression expression = element.cachedNode; | |
| 1067 sourceMappings.add(new SourceMappingEntry( | |
| 1068 sourceFile, expression.getBeginToken().charOffset, beginPosition)); | |
| 1069 sourceMappings.add(new SourceMappingEntry( | |
| 1070 sourceFile, expression.getEndToken().charOffset, endPosition)); | |
| 1071 } | |
| 1072 } | |
| OLD | NEW |