use of org.checkerframework.framework.type.AnnotatedTypeMirror in project checker-framework by typetools.
the class InitializationAnnotatedTypeFactory method computeFieldAccessType.
/**
* Determine the type of a field access (implicit or explicit) based on the receiver type and
* the declared annotations for the field.
*
* @param type type of the field access expression
* @param declaredFieldAnnotations annotations on the element
* @param receiverType inferred annotations of the receiver
*/
private void computeFieldAccessType(AnnotatedTypeMirror type, Collection<? extends AnnotationMirror> declaredFieldAnnotations, AnnotatedTypeMirror receiverType, AnnotatedTypeMirror fieldAnnotations, Element element) {
// not necessary for primitive fields
if (TypesUtils.isPrimitive(type.getUnderlyingType())) {
return;
}
// annotation on the field
if (AnnotationUtils.containsSameIgnoringValues(fieldAnnotations.getAnnotations(), UNCLASSIFIED)) {
return;
}
if (isUnclassified(receiverType) || isFree(receiverType)) {
TypeMirror fieldDeclarationType = element.getEnclosingElement().asType();
boolean isInitializedForFrame = isInitializedForFrame(receiverType, fieldDeclarationType);
if (isInitializedForFrame) {
// The receiver is initialized for this frame.
// Change the type of the field to @UnknownInitialization or @Raw so that
// anything can be assigned to this field.
type.replaceAnnotation(UNCLASSIFIED);
} else if (computingAnnotatedTypeMirrorOfLHS) {
// The receiver is not initialized for this frame, but the type of a lhs is being
// computed.
// Change the type of the field to @UnknownInitialization or @Raw so that
// anything can be assigned to this field.
type.replaceAnnotation(UNCLASSIFIED);
} else {
// The receiver is not initialized for this frame and the type being computed is not
// a LHS.
// Replace all annotations with the top annotation for that hierarchy.
type.clearAnnotations();
type.addAnnotations(qualHierarchy.getTopAnnotations());
}
if (!AnnotationUtils.containsSame(declaredFieldAnnotations, NOT_ONLY_COMMITTED) || !useFbc) {
// add root annotation for all other hierarchies, and
// Committed for the commitment hierarchy
type.replaceAnnotation(COMMITTED);
}
}
}
use of org.checkerframework.framework.type.AnnotatedTypeMirror in project checker-framework by typetools.
the class InitializationVisitor method checkContract.
@Override
protected boolean checkContract(Receiver expr, AnnotationMirror necessaryAnnotation, AnnotationMirror inferredAnnotation, CFAbstractStore<?, ?> store) {
// also use the information about initialized fields to check contracts
final AnnotationMirror invariantAnno = atypeFactory.getFieldInvariantAnnotation();
if (atypeFactory.getQualifierHierarchy().isSubtype(invariantAnno, necessaryAnnotation)) {
if (expr instanceof FieldAccess) {
FieldAccess fa = (FieldAccess) expr;
if (fa.getReceiver() instanceof ThisReference || fa.getReceiver() instanceof ClassName) {
@SuppressWarnings("unchecked") Store s = (Store) store;
if (s.isFieldInitialized(fa.getField())) {
AnnotatedTypeMirror fieldType = atypeFactory.getAnnotatedType(fa.getField());
// is this an invariant-field?
if (AnnotationUtils.containsSame(fieldType.getAnnotations(), invariantAnno)) {
return true;
}
}
} else {
Set<AnnotationMirror> recvAnnoSet;
@SuppressWarnings("unchecked") Value value = (Value) store.getValue(fa.getReceiver());
if (value != null) {
recvAnnoSet = value.getAnnotations();
} else if (fa.getReceiver() instanceof LocalVariable) {
Element elem = ((LocalVariable) fa.getReceiver()).getElement();
AnnotatedTypeMirror recvType = atypeFactory.getAnnotatedType(elem);
recvAnnoSet = recvType.getAnnotations();
} else {
// Is there anything better we could do?
return false;
}
boolean isRecvCommitted = false;
for (AnnotationMirror anno : recvAnnoSet) {
if (atypeFactory.isCommitted(anno)) {
isRecvCommitted = true;
}
}
AnnotatedTypeMirror fieldType = atypeFactory.getAnnotatedType(fa.getField());
// has the invariant type.
if (isRecvCommitted && AnnotationUtils.containsSame(fieldType.getAnnotations(), invariantAnno)) {
return true;
}
}
}
}
return super.checkContract(expr, necessaryAnnotation, inferredAnnotation, store);
}
use of org.checkerframework.framework.type.AnnotatedTypeMirror in project checker-framework by typetools.
the class LockVisitor method visitArrayAccess.
@Override
public Void visitArrayAccess(ArrayAccessTree tree, Void p) {
AnnotatedTypeMirror atmOfReceiver = atypeFactory.getAnnotatedType(tree.getExpression());
AnnotationMirror gb = atmOfReceiver.getEffectiveAnnotationInHierarchy(atypeFactory.GUARDEDBYUNKNOWN);
checkLock(tree.getExpression(), gb);
return super.visitArrayAccess(tree, p);
}
use of org.checkerframework.framework.type.AnnotatedTypeMirror 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);
}
use of org.checkerframework.framework.type.AnnotatedTypeMirror in project checker-framework by typetools.
the class LockVisitor method visitMemberSelect.
@Override
public Void visitMemberSelect(MemberSelectTree tree, Void p) {
if (TreeUtils.isFieldAccess(tree)) {
AnnotatedTypeMirror atmOfReceiver = atypeFactory.getAnnotatedType(tree.getExpression());
// it.
if (atmOfReceiver.getKind() != TypeKind.VOID) {
AnnotationMirror gb = atmOfReceiver.getEffectiveAnnotationInHierarchy(atypeFactory.GUARDEDBYUNKNOWN);
checkLock(tree.getExpression(), gb);
}
}
return super.visitMemberSelect(tree, p);
}
Aggregations