Index: compiler/java/com/google/dart/compiler/resolver/Resolver.java |
diff --git a/compiler/java/com/google/dart/compiler/resolver/Resolver.java b/compiler/java/com/google/dart/compiler/resolver/Resolver.java |
index 7a376e56aceddda5c6c6eccb74c19853ddaf9ea4..46b5f2047b79979fbcb4252bd5bb76d44bfd6f26 100644 |
--- a/compiler/java/com/google/dart/compiler/resolver/Resolver.java |
+++ b/compiler/java/com/google/dart/compiler/resolver/Resolver.java |
@@ -246,8 +246,21 @@ public class Resolver { |
element.getNode().accept(this); |
} |
+ boolean testForAllConstantFields = false; |
for (Element element : classElement.getConstructors()) { |
element.getNode().accept(this); |
+ if (element.getModifiers().isConstant()) { |
+ testForAllConstantFields = true; |
+ } |
+ } |
+ |
+ if (testForAllConstantFields) { |
+ InterfaceType interfaceType = classElement.getType(); |
+ while (interfaceType != null && interfaceType != typeProvider.getObjectType()) { |
+ ClassElement interfaceElement = interfaceType.getElement(); |
+ constVerifyMembers(interfaceElement.getMembers(), classElement, interfaceElement); |
+ interfaceType = interfaceElement.getSupertype(); |
+ } |
} |
checkRedirectConstructorCycle(classElement.getConstructors(), context); |
@@ -290,6 +303,23 @@ public class Resolver { |
return classElement; |
} |
+ private void constVerifyMembers(Iterable<Element> members, ClassElement originalClass, |
+ ClassElement currentClass) { |
+ for (Element element : members) { |
+ Modifiers modifiers = element.getModifiers(); |
+ if (ElementKind.of(element).equals(ElementKind.FIELD) && !modifiers.isFinal() |
+ && !modifiers.isAbstractField()) { |
+ FieldElement field = (FieldElement) element; |
+ DartNode errorNode = field.getSetter() == null ? element.getNode() |
+ : field.getSetter().getNode(); |
+ onError(errorNode, currentClass == originalClass |
+ ? ResolverErrorCode.CONST_CLASS_WITH_NONFINAL_FIELDS |
+ : ResolverErrorCode.CONST_CLASS_WITH_INHERITED_NONFINAL_FIELDS, |
+ originalClass.getName(), field.getName(), currentClass.getName()); |
+ } |
+ } |
+ } |
+ |
/** |
* Sets the type in the AST of the default clause of an inteterface so that the type |
* parameters to resolve back to the default class. |