Chromium Code Reviews| Index: sdk/lib/_internal/compiler/implementation/resolution/members.dart |
| diff --git a/sdk/lib/_internal/compiler/implementation/resolution/members.dart b/sdk/lib/_internal/compiler/implementation/resolution/members.dart |
| index aca4608e3a976031939e4b2b60844cf9b84ffe5c..34b89e9840cd92002363d55caaf48ac6dffad5dc 100644 |
| --- a/sdk/lib/_internal/compiler/implementation/resolution/members.dart |
| +++ b/sdk/lib/_internal/compiler/implementation/resolution/members.dart |
| @@ -336,7 +336,7 @@ class ResolverTask extends CompilerTask { |
| TreeElements elements = |
| compiler.enqueuer.resolution.getCachedElements(element); |
| if (elements != null) { |
| - assert(isConstructor); |
| + assert(isConstructor || element.isFactoryConstructor()); |
|
karlklose
2013/09/05 12:43:42
Remember to remove this when rebasing with my chan
Johnni Winther
2013/09/06 06:22:41
Done.
|
| return elements; |
| } |
| if (element.isSynthesized) { |
| @@ -662,6 +662,8 @@ class ResolverTask extends CompilerTask { |
| if (cls.isObject(compiler)) return; |
| // TODO(johnniwinther): Should this be done on the implementation element as |
| // well? |
| + List<Element> constConstructors = <Element>[]; |
| + List<Element> nonFinalInstanceFields = <Element>[]; |
| cls.forEachMember((holder, member) { |
| compiler.withCurrentElement(member, () { |
| // Perform various checks as side effect of "computing" the type. |
| @@ -684,12 +686,40 @@ class ResolverTask extends CompilerTask { |
| MessageKind.ILLEGAL_CONSTRUCTOR_MODIFIERS, |
| {'modifiers': mismatchedFlags}); |
| } |
| + if (member.modifiers.isConst()) { |
| + constConstructors.add(member); |
| + } |
| + } |
| + if (member.isField()) { |
| + if (!member.modifiers.isStatic() && |
| + !member.modifiers.isFinal()) { |
| + nonFinalInstanceFields.add(member); |
| + } |
| } |
| checkAbstractField(member); |
| checkValidOverride(member, cls.lookupSuperMember(member.name)); |
| checkUserDefinableOperator(member); |
| }); |
| }); |
| + if (!constConstructors.isEmpty && !nonFinalInstanceFields.isEmpty) { |
| + if (constConstructors.length == 1) { |
| + compiler.reportError(constConstructors[0], |
| + MessageKind.CONST_CONSTRUCTOR_WITH_NONFINAL_FIELDS, |
| + {'className': cls.name}); |
| + } else { |
| + compiler.reportError(cls, |
|
karlklose
2013/09/05 12:43:42
Move the call out of the if and compute the Spanna
Johnni Winther
2013/09/06 06:22:41
Done.
|
| + MessageKind.CONST_CONSTRUCTOR_WITH_NONFINAL_FIELDS, |
| + {'className': cls.name}); |
| + for (Element constructor in constConstructors) { |
| + compiler.reportInfo(constructor, |
| + MessageKind.CONST_CONSTRUCTOR_WITH_NONFINAL_FIELDS_CONSTRUCTOR); |
| + } |
| + } |
| + for (Element field in nonFinalInstanceFields) { |
| + compiler.reportInfo(field, |
| + MessageKind.CONST_CONSTRUCTOR_WITH_NONFINAL_FIELDS_FIELD); |
| + } |
| + } |
| } |
| void checkAbstractField(Element member) { |
| @@ -2715,7 +2745,6 @@ class ResolverVisitor extends MappingVisitor<Element> { |
| return true; |
| } |
| - |
| /** |
| * Try to resolve the constructor that is referred to by [node]. |
| * Note: this function may return an ErroneousFunctionElement instead of |