use of org.checkerframework.framework.source.Result in project checker-framework by typetools.
the class BaseTypeValidator method isValid.
/**
* The entry point to the type validator. Validate the type against the given tree. Neither this
* method nor visit should be called directly by a visitor, only use {@link
* BaseTypeVisitor#validateTypeOf(Tree)}.
*
* @param type the type to validate
* @param tree the tree from which the type originated. If the tree is a method tree, validate
* its return type. If the tree is a variable tree, validate its field type.
* @return true, iff the type is valid
*/
@Override
public boolean isValid(AnnotatedTypeMirror type, Tree tree) {
Result result = isValidType(atypeFactory.getQualifierHierarchy(), type);
if (result.isFailure()) {
checker.report(result, tree);
return false;
}
this.isValid = true;
visit(type, tree);
return this.isValid;
}
use of org.checkerframework.framework.source.Result in project checker-framework by typetools.
the class BaseTypeVisitor method checkFieldInvariantDeclarations.
/**
* Check that the field invariant declaration annotations meet the following requirements:
*
* <ol>
* <!-- The item numbering is referred to in the body of the method.-->
* <li value="1">If the superclass of {@code classTree} has a field invariant, then the field
* invariant for {@code classTree} must include all the fields in the superclass invariant
* and those fields' annotations must be a subtype (or equal) to the annotations for those
* fields in the superclass.
* <li value="2">The fields in the invariant must be a.) final and b.) declared in a
* superclass of {@code classTree}.
* <li value="3">The qualifier for each field must be a subtype of the annotation on the
* declaration of that field.
* <li value="4">The field invariant has an equal number of fields and qualifiers, or it has
* one qualifier and at least one field.
* </ol>
*
* @param classTree class that might have a field invariant
* @checker_framework.manual #field-invariants Field invariants
*/
protected void checkFieldInvariantDeclarations(ClassTree classTree) {
TypeElement elt = TreeUtils.elementFromDeclaration(classTree);
FieldInvariants invariants = atypeFactory.getFieldInvariants(elt);
if (invariants == null) {
// No invariants to check
return;
}
// Where to issue an error, if any.
Tree errorTree = atypeFactory.getFieldInvariantAnnotationTree(classTree.getModifiers().getAnnotations());
if (errorTree == null) {
// If the annotation was inherited, then there is no annotation tree, so issue the
// error on the class.
errorTree = classTree;
}
// Checks #4 (see method Javadoc)
if (!invariants.isWellFormed()) {
checker.report(Result.failure("field.invariant.not.wellformed"), errorTree);
return;
}
TypeMirror superClass = elt.getSuperclass();
List<String> fieldsNotFound = new ArrayList<>(invariants.getFields());
Set<VariableElement> fieldElts = ElementUtils.findFieldsInTypeOrSuperType(superClass, fieldsNotFound);
// Checks that fields are declared in super class. (#2b)
if (!fieldsNotFound.isEmpty()) {
String notFoundString = PluginUtil.join(", ", fieldsNotFound);
checker.report(Result.failure("field.invariant.not.found", notFoundString), errorTree);
}
FieldInvariants superInvar = atypeFactory.getFieldInvariants(TypesUtils.getTypeElement(superClass));
if (superInvar != null) {
// Checks #3 (see method Javadoc)
Result superError = invariants.isSuperInvariant(superInvar, atypeFactory);
if (superError != null) {
checker.report(superError, errorTree);
}
}
List<String> notFinal = new ArrayList<>();
for (VariableElement field : fieldElts) {
String fieldName = field.getSimpleName().toString();
if (!ElementUtils.isFinal(field)) {
notFinal.add(fieldName);
}
AnnotatedTypeMirror type = atypeFactory.getAnnotatedType(field);
List<AnnotationMirror> annos = invariants.getQualifiersFor(field.getSimpleName());
for (AnnotationMirror invariantAnno : annos) {
AnnotationMirror declaredAnno = type.getEffectiveAnnotationInHierarchy(invariantAnno);
if (declaredAnno == null) {
// invariant anno isn't in this hierarchy
continue;
}
if (!atypeFactory.getQualifierHierarchy().isSubtype(invariantAnno, declaredAnno)) {
// Checks #3
checker.report(Result.failure("field.invariant.not.subtype", fieldName, invariantAnno, declaredAnno), errorTree);
}
}
}
// Checks #2a
if (!notFinal.isEmpty()) {
String notFinalString = PluginUtil.join(", ", notFinal);
checker.report(Result.failure("field.invariant.not.final", notFinalString), errorTree);
}
}
use of org.checkerframework.framework.source.Result in project checker-framework by typetools.
the class CFAbstractTransfer method processPostconditionsAndConditionalPostconditions.
private void processPostconditionsAndConditionalPostconditions(MethodInvocationNode n, Tree tree, S thenStore, S elseStore, Set<? extends Contract> postconditions) {
FlowExpressionContext flowExprContext = null;
for (Contract p : postconditions) {
String expression = p.expression;
AnnotationMirror anno = p.annotation;
if (flowExprContext == null) {
flowExprContext = FlowExpressionContext.buildContextForMethodUse(n, analysis.checker.getContext());
}
TreePath localScope = analysis.atypeFactory.getPath(tree);
anno = standardizeAnnotationFromContract(anno, flowExprContext, localScope);
try {
FlowExpressions.Receiver r = FlowExpressionParseUtil.parse(expression, flowExprContext, localScope, false);
if (p.kind == Contract.Kind.CONDITIONALPOSTCONDTION) {
if (((ConditionalPostcondition) p).annoResult) {
thenStore.insertValue(r, anno);
} else {
elseStore.insertValue(r, anno);
}
} else {
thenStore.insertValue(r, anno);
}
} catch (FlowExpressionParseException e) {
Result result;
if (e.isFlowParseError()) {
Object[] args = new Object[e.args.length + 1];
args[0] = ElementUtils.getVerboseName(TreeUtils.elementFromUse(n.getTree()));
System.arraycopy(e.args, 0, args, 1, e.args.length);
result = Result.failure("flowexpr.parse.error.postcondition", args);
} else {
result = e.getResult();
}
// report errors here
analysis.checker.report(result, tree);
}
}
}
Aggregations