| 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 library dart2js.resolution.members; | 5 library dart2js.resolution.members; |
| 6 | 6 |
| 7 import '../common.dart'; | 7 import '../common.dart'; |
| 8 import '../common/names.dart' show Selectors; | 8 import '../common/names.dart' show Selectors; |
| 9 import '../common/resolution.dart' show Feature; | 9 import '../common/resolution.dart' show Feature; |
| 10 import '../compiler.dart' show Compiler; | 10 import '../compiler.dart' show Compiler; |
| (...skipping 3826 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 3837 if (!isInvalid) { | 3837 if (!isInvalid) { |
| 3838 // [constructor] might be the implementation element | 3838 // [constructor] might be the implementation element |
| 3839 // and only declaration elements may be registered. | 3839 // and only declaration elements may be registered. |
| 3840 registry.registerStaticUse(new StaticUse.constructorInvoke( | 3840 registry.registerStaticUse(new StaticUse.constructorInvoke( |
| 3841 constructor.declaration, callStructure)); | 3841 constructor.declaration, callStructure)); |
| 3842 // TODO(johniwinther): Avoid registration of `type` in face of redirecting | 3842 // TODO(johniwinther): Avoid registration of `type` in face of redirecting |
| 3843 // factory constructors. | 3843 // factory constructors. |
| 3844 registry.registerTypeUse(new TypeUse.instantiation(type)); | 3844 registry.registerTypeUse(new TypeUse.instantiation(type)); |
| 3845 } | 3845 } |
| 3846 | 3846 |
| 3847 ResolutionResult resolutionResult = const NoneResult(); |
| 3847 if (node.isConst) { | 3848 if (node.isConst) { |
| 3848 bool isValidAsConstant = !isInvalid && constructor.isConst; | 3849 bool isValidAsConstant = !isInvalid && constructor.isConst; |
| 3849 | 3850 |
| 3850 if (constructor == compiler.symbolConstructor) { | 3851 if (constructor == compiler.symbolConstructor) { |
| 3851 Node argumentNode = node.send.arguments.head; | 3852 Node argumentNode = node.send.arguments.head; |
| 3852 ConstantExpression constant = compiler.resolver.constantCompiler | 3853 ConstantExpression constant = compiler.resolver.constantCompiler |
| 3853 .compileNode(argumentNode, registry.mapping); | 3854 .compileNode(argumentNode, registry.mapping); |
| 3854 ConstantValue name = compiler.constants.getConstantValue(constant); | 3855 ConstantValue name = compiler.constants.getConstantValue(constant); |
| 3855 if (!name.isString) { | 3856 if (!name.isString) { |
| 3856 DartType type = name.getType(coreTypes); | 3857 DartType type = name.getType(coreTypes); |
| (...skipping 16 matching lines...) Expand all Loading... |
| 3873 reporter.reportErrorMessage( | 3874 reporter.reportErrorMessage( |
| 3874 node.send.selector, MessageKind.TYPE_VARIABLE_IN_CONSTANT); | 3875 node.send.selector, MessageKind.TYPE_VARIABLE_IN_CONSTANT); |
| 3875 isValidAsConstant = false; | 3876 isValidAsConstant = false; |
| 3876 isInvalid = true; | 3877 isInvalid = true; |
| 3877 } | 3878 } |
| 3878 | 3879 |
| 3879 if (result.isDeferred) { | 3880 if (result.isDeferred) { |
| 3880 isValidAsConstant = false; | 3881 isValidAsConstant = false; |
| 3881 } | 3882 } |
| 3882 | 3883 |
| 3884 // Callback hook for when the compile-time constant evaluator has |
| 3885 // analyzed the constant. |
| 3886 // TODO(johnniwinther): Remove this when all constants are computed |
| 3887 // in resolution. |
| 3888 Function onAnalyzed; |
| 3883 if (isValidAsConstant && | 3889 if (isValidAsConstant && |
| 3884 argumentsResult.isValidAsConstant && | 3890 argumentsResult.isValidAsConstant && |
| 3885 // TODO(johnniwinther): Remove this when all constants are computed | 3891 // TODO(johnniwinther): Remove this when all constants are computed |
| 3886 // in resolution. | 3892 // in resolution. |
| 3887 !constructor.isFromEnvironmentConstructor) { | 3893 !constructor.isFromEnvironmentConstructor) { |
| 3888 CallStructure callStructure = argumentsResult.callStructure; | 3894 CallStructure callStructure = argumentsResult.callStructure; |
| 3889 List<ConstantExpression> arguments = argumentsResult.constantArguments; | 3895 List<ConstantExpression> arguments = argumentsResult.constantArguments; |
| 3890 | 3896 |
| 3891 ConstructedConstantExpression constant = | 3897 ConstructedConstantExpression constant = |
| 3892 new ConstructedConstantExpression( | 3898 new ConstructedConstantExpression( |
| 3893 type, constructor, callStructure, arguments); | 3899 type, constructor, callStructure, arguments); |
| 3894 registry.registerNewStructure(node, | 3900 registry.registerNewStructure(node, |
| 3895 new ConstInvokeStructure(ConstantInvokeKind.CONSTRUCTED, constant)); | 3901 new ConstInvokeStructure(ConstantInvokeKind.CONSTRUCTED, constant)); |
| 3896 return new ConstantResult(node, constant); | 3902 resolutionResult = new ConstantResult(node, constant); |
| 3897 } else if (isInvalid) { | 3903 } else if (isInvalid) { |
| 3898 // Known to be non-constant. | 3904 // Known to be non-constant. |
| 3899 kind == ConstructorAccessKind.NON_CONSTANT_CONSTRUCTOR; | 3905 kind == ConstructorAccessKind.NON_CONSTANT_CONSTRUCTOR; |
| 3900 registry.registerNewStructure( | 3906 registry.registerNewStructure( |
| 3901 node, | 3907 node, |
| 3902 new NewInvokeStructure( | 3908 new NewInvokeStructure( |
| 3903 new ConstructorAccessSemantics(kind, constructor, type), | 3909 new ConstructorAccessSemantics(kind, constructor, type), |
| 3904 selector)); | 3910 selector)); |
| 3905 } else { | 3911 } else { |
| 3906 // Might be valid but we don't know for sure. The compile-time constant | 3912 // Might be valid but we don't know for sure. The compile-time constant |
| 3907 // evaluator will compute the actual constant as a deferred action. | 3913 // evaluator will compute the actual constant as a deferred action. |
| 3908 registry.registerNewStructure( | 3914 LateConstInvokeStructure structure = |
| 3909 node, new LateConstInvokeStructure(registry.mapping)); | 3915 new LateConstInvokeStructure(registry.mapping); |
| 3916 // TODO(johnniwinther): Avoid registering the |
| 3917 // [LateConstInvokeStructure]; it might not be necessary. |
| 3918 registry.registerNewStructure(node, structure); |
| 3919 onAnalyzed = () { |
| 3920 registry.registerNewStructure(node, structure.resolve(node)); |
| 3921 }; |
| 3910 } | 3922 } |
| 3923 |
| 3924 analyzeConstantDeferred(node, onAnalyzed: onAnalyzed); |
| 3911 } else { | 3925 } else { |
| 3912 // Not constant. | 3926 // Not constant. |
| 3913 if (constructor == compiler.symbolConstructor && | 3927 if (constructor == compiler.symbolConstructor && |
| 3914 !compiler.mirrorUsageAnalyzerTask.hasMirrorUsage(enclosingElement)) { | 3928 !compiler.mirrorUsageAnalyzerTask.hasMirrorUsage(enclosingElement)) { |
| 3915 reporter.reportHintMessage(node.newToken, MessageKind.NON_CONST_BLOAT, | 3929 reporter.reportHintMessage(node.newToken, MessageKind.NON_CONST_BLOAT, |
| 3916 {'name': coreClasses.symbolClass.name}); | 3930 {'name': coreClasses.symbolClass.name}); |
| 3917 } | 3931 } |
| 3918 registry.registerNewStructure( | 3932 registry.registerNewStructure( |
| 3919 node, | 3933 node, |
| 3920 new NewInvokeStructure( | 3934 new NewInvokeStructure( |
| 3921 new ConstructorAccessSemantics(kind, constructor, type), | 3935 new ConstructorAccessSemantics(kind, constructor, type), |
| 3922 selector)); | 3936 selector)); |
| 3923 } | 3937 } |
| 3924 | 3938 |
| 3925 return const NoneResult(); | 3939 return resolutionResult; |
| 3926 } | 3940 } |
| 3927 | 3941 |
| 3928 void checkConstMapKeysDontOverrideEquals( | 3942 void checkConstMapKeysDontOverrideEquals( |
| 3929 Spannable spannable, MapConstantValue map) { | 3943 Spannable spannable, MapConstantValue map) { |
| 3930 for (ConstantValue key in map.keys) { | 3944 for (ConstantValue key in map.keys) { |
| 3931 if (!key.isObject) continue; | 3945 if (!key.isObject) continue; |
| 3932 ObjectConstantValue objectConstant = key; | 3946 ObjectConstantValue objectConstant = key; |
| 3933 DartType keyType = objectConstant.type; | 3947 DartType keyType = objectConstant.type; |
| 3934 ClassElement cls = keyType.element; | 3948 ClassElement cls = keyType.element; |
| 3935 if (cls == coreClasses.stringClass) continue; | 3949 if (cls == coreClasses.stringClass) continue; |
| (...skipping 13 matching lines...) Expand all Loading... |
| 3949 assert(invariant(node, compiler.compilationFailed)); | 3963 assert(invariant(node, compiler.compilationFailed)); |
| 3950 return; | 3964 return; |
| 3951 } | 3965 } |
| 3952 | 3966 |
| 3953 ConstantValue value = compiler.constants.getConstantValue(constant); | 3967 ConstantValue value = compiler.constants.getConstantValue(constant); |
| 3954 if (value.isMap) { | 3968 if (value.isMap) { |
| 3955 checkConstMapKeysDontOverrideEquals(node, value); | 3969 checkConstMapKeysDontOverrideEquals(node, value); |
| 3956 } | 3970 } |
| 3957 } | 3971 } |
| 3958 | 3972 |
| 3959 void analyzeConstantDeferred(Node node, {bool enforceConst: true}) { | 3973 void analyzeConstantDeferred(Node node, |
| 3974 {bool enforceConst: true, void onAnalyzed()}) { |
| 3960 addDeferredAction(enclosingElement, () { | 3975 addDeferredAction(enclosingElement, () { |
| 3961 analyzeConstant(node, enforceConst: enforceConst); | 3976 analyzeConstant(node, enforceConst: enforceConst); |
| 3977 if (onAnalyzed != null) { |
| 3978 onAnalyzed(); |
| 3979 } |
| 3962 }); | 3980 }); |
| 3963 } | 3981 } |
| 3964 | 3982 |
| 3965 bool validateSymbol(Node node, String name, {bool reportError: true}) { | 3983 bool validateSymbol(Node node, String name, {bool reportError: true}) { |
| 3966 if (name.isEmpty) return true; | 3984 if (name.isEmpty) return true; |
| 3967 if (name.startsWith('_')) { | 3985 if (name.startsWith('_')) { |
| 3968 if (reportError) { | 3986 if (reportError) { |
| 3969 reporter.reportErrorMessage( | 3987 reporter.reportErrorMessage( |
| 3970 node, MessageKind.PRIVATE_IDENTIFIER, {'value': name}); | 3988 node, MessageKind.PRIVATE_IDENTIFIER, {'value': name}); |
| 3971 } | 3989 } |
| (...skipping 687 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 4659 } | 4677 } |
| 4660 return const NoneResult(); | 4678 return const NoneResult(); |
| 4661 } | 4679 } |
| 4662 } | 4680 } |
| 4663 | 4681 |
| 4664 /// Looks up [name] in [scope] and unwraps the result. | 4682 /// Looks up [name] in [scope] and unwraps the result. |
| 4665 Element lookupInScope( | 4683 Element lookupInScope( |
| 4666 DiagnosticReporter reporter, Node node, Scope scope, String name) { | 4684 DiagnosticReporter reporter, Node node, Scope scope, String name) { |
| 4667 return Elements.unwrap(scope.lookup(name), reporter, node); | 4685 return Elements.unwrap(scope.lookup(name), reporter, node); |
| 4668 } | 4686 } |
| OLD | NEW |