Search in sources :

Example 1 with GuardedByBottom

use of org.checkerframework.checker.lock.qual.GuardedByBottom in project checker-framework by typetools.

the class LockVisitor method commonAssignmentCheck.

@Override
protected void commonAssignmentCheck(AnnotatedTypeMirror varType, AnnotatedTypeMirror valueType, Tree valueTree, @CompilerMessageKey String errorKey) {
    Kind valueTreeKind = valueTree.getKind();
    switch(valueTreeKind) {
        case NEW_CLASS:
        case NEW_ARRAY:
            // Do NOT do this if the LHS is @GuardedByBottom.
            if (!varType.hasAnnotation(GuardedByBottom.class)) {
                return;
            }
            break;
        case INT_LITERAL:
        case LONG_LITERAL:
        case FLOAT_LITERAL:
        case DOUBLE_LITERAL:
        case BOOLEAN_LITERAL:
        case CHAR_LITERAL:
        case STRING_LITERAL:
            // Do NOT do this if the LHS is @GuardedByBottom.
            if (!varType.hasAnnotation(GuardedByBottom.class)) {
                return;
            }
            break;
        default:
    }
    if (varType.hasAnnotation(GuardSatisfied.class)) {
        if (valueType.hasAnnotation(GuardedBy.class)) {
            checkLock(valueTree, valueType.getAnnotation(GuardedBy.class));
            return;
        } else if (valueType.hasAnnotation(GuardSatisfied.class)) {
            if (!errorKey.equals("argument.type.incompatible")) {
                // If both @GuardSatisfied have no index, the assignment is not allowed because
                // the LHS and RHS expressions may be guarded by different lock expressions.
                // The assignment is allowed when matching a formal parameter to an actual
                // parameter (see the if block above).
                int varTypeGuardSatisfiedIndex = atypeFactory.getGuardSatisfiedIndex(varType);
                int valueTypeGuardSatisfiedIndex = atypeFactory.getGuardSatisfiedIndex(valueType);
                if (varTypeGuardSatisfiedIndex == -1 && valueTypeGuardSatisfiedIndex == -1) {
                    checker.report(Result.failure("guardsatisfied.assignment.disallowed", varType, valueType), valueTree);
                }
            } else {
                return;
            }
        } else if (!atypeFactory.getTypeHierarchy().isSubtype(valueType, varType)) {
            // Special case: replace the @GuardSatisfied primary annotation on the LHS with
            // @GuardedBy({}) and see if it type checks.
            AnnotatedTypeMirror varType2 = // TODO: Would shallowCopy be sufficient?
            varType.deepCopy();
            varType2.replaceAnnotation(atypeFactory.GUARDEDBY);
            if (atypeFactory.getTypeHierarchy().isSubtype(valueType, varType2)) {
                return;
            }
        }
    }
    super.commonAssignmentCheck(varType, valueType, valueTree, errorKey);
}
Also used : GuardedBy(org.checkerframework.checker.lock.qual.GuardedBy) GuardedByBottom(org.checkerframework.checker.lock.qual.GuardedByBottom) TypeKind(javax.lang.model.type.TypeKind) Kind(com.sun.source.tree.Tree.Kind) ElementKind(javax.lang.model.element.ElementKind) AnnotatedTypeMirror(org.checkerframework.framework.type.AnnotatedTypeMirror) GuardSatisfied(org.checkerframework.checker.lock.qual.GuardSatisfied)

Aggregations

Kind (com.sun.source.tree.Tree.Kind)1 ElementKind (javax.lang.model.element.ElementKind)1 TypeKind (javax.lang.model.type.TypeKind)1 GuardSatisfied (org.checkerframework.checker.lock.qual.GuardSatisfied)1 GuardedBy (org.checkerframework.checker.lock.qual.GuardedBy)1 GuardedByBottom (org.checkerframework.checker.lock.qual.GuardedByBottom)1 AnnotatedTypeMirror (org.checkerframework.framework.type.AnnotatedTypeMirror)1