use of org.checkerframework.dataflow.expression.ThisReference in project checker-framework by typetools.
the class StringToJavaExpression method atTypeDecl.
/**
* Parses a string to a {@link JavaExpression} as if it were written at {@code typeElement}.
*
* @param expression a Java expression to parse
* @param typeElement type element at which {@code expression} is parsed
* @param checker checker used to get the {@link
* javax.annotation.processing.ProcessingEnvironment} and current {@link
* com.sun.source.tree.CompilationUnitTree}
* @return a {@code JavaExpression} for {@code expression}
* @throws JavaExpressionParseException if {@code expression} cannot be parsed
*/
static JavaExpression atTypeDecl(String expression, TypeElement typeElement, SourceChecker checker) throws JavaExpressionParseException {
ThisReference thisReference = new ThisReference(typeElement.asType());
List<FormalParameter> parameters = null;
return JavaExpressionParseUtil.parse(expression, typeElement.asType(), thisReference, parameters, null, checker.getPathToCompilationUnit(), checker.getProcessingEnvironment());
}
use of org.checkerframework.dataflow.expression.ThisReference in project checker-framework by typetools.
the class StringToJavaExpression method atLambdaParameter.
/**
* Parses a string as if it were written at one of the parameters of {@code lambdaTree}.
* Parameters of the lambda are expressed as {@link LocalVariable}s.
*
* @param expression a Java expression to parse
* @param lambdaTree the lambda tree
* @param parentPath path to the parent of {@code lambdaTree}; required because the expression can
* reference final local variables of the enclosing method
* @param checker checker used to get the {@link
* javax.annotation.processing.ProcessingEnvironment} and current {@link
* com.sun.source.tree.CompilationUnitTree}
* @return a {@code JavaExpression} for {@code expression}
* @throws JavaExpressionParseException if {@code expression} cannot be parsed
*/
static JavaExpression atLambdaParameter(String expression, LambdaExpressionTree lambdaTree, TreePath parentPath, SourceChecker checker) throws JavaExpressionParseException {
TypeMirror enclosingType = TreeUtils.typeOf(TreePathUtil.enclosingClass(parentPath));
JavaExpression receiver = JavaExpression.getPseudoReceiver(parentPath, enclosingType);
// If receiver isn't a ThisReference, then the lambda is in a static context and "this"
// cannot be referenced in the expression.
ThisReference thisReference = receiver instanceof ThisReference ? (ThisReference) receiver : null;
List<JavaExpression> paramsAsLocals = new ArrayList<>(lambdaTree.getParameters().size());
List<FormalParameter> parameters = new ArrayList<>(lambdaTree.getParameters().size());
int oneBasedIndex = 1;
for (VariableTree arg : lambdaTree.getParameters()) {
LocalVariable param = (LocalVariable) JavaExpression.fromVariableTree(arg);
paramsAsLocals.add(param);
parameters.add(new FormalParameter(oneBasedIndex, (VariableElement) param.getElement()));
oneBasedIndex++;
}
JavaExpression javaExpr = JavaExpressionParseUtil.parse(expression, enclosingType, thisReference, parameters, parentPath, checker.getPathToCompilationUnit(), checker.getProcessingEnvironment());
return ViewpointAdaptJavaExpression.viewpointAdapt(javaExpr, paramsAsLocals);
}
use of org.checkerframework.dataflow.expression.ThisReference in project checker-framework by typetools.
the class InitializationVisitor method checkContract.
@Override
protected boolean checkContract(JavaExpression 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) || !(expr instanceof FieldAccess)) {
return super.checkContract(expr, necessaryAnnotation, inferredAnnotation, store);
}
if (expr.containsUnknown()) {
return false;
}
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 {
@SuppressWarnings("unchecked") Value value = (Value) store.getValue(fa.getReceiver());
Set<AnnotationMirror> receiverAnnoSet;
if (value != null) {
receiverAnnoSet = value.getAnnotations();
} else if (fa.getReceiver() instanceof LocalVariable) {
Element elem = ((LocalVariable) fa.getReceiver()).getElement();
AnnotatedTypeMirror receiverType = atypeFactory.getAnnotatedType(elem);
receiverAnnoSet = receiverType.getAnnotations();
} else {
// Is there anything better we could do?
return false;
}
boolean isReceiverInitialized = false;
for (AnnotationMirror anno : receiverAnnoSet) {
if (atypeFactory.isInitialized(anno)) {
isReceiverInitialized = true;
}
}
AnnotatedTypeMirror fieldType = atypeFactory.getAnnotatedType(fa.getField());
// has the invariant type.
if (isReceiverInitialized && AnnotationUtils.containsSame(fieldType.getAnnotations(), invariantAnno)) {
return true;
}
}
return super.checkContract(expr, necessaryAnnotation, inferredAnnotation, store);
}
use of org.checkerframework.dataflow.expression.ThisReference in project checker-framework by typetools.
the class InitializationStore method insertValue.
/**
* {@inheritDoc}
*
* <p>If the receiver is a field, and has an invariant annotation, then it can be considered
* initialized.
*/
@Override
public void insertValue(JavaExpression je, V value, boolean permitNondeterministic) {
if (!shouldInsert(je, value, permitNondeterministic)) {
return;
}
InitializationAnnotatedTypeFactory<?, ?, ?, ?> atypeFactory = (InitializationAnnotatedTypeFactory<?, ?, ?, ?>) analysis.getTypeFactory();
QualifierHierarchy qualifierHierarchy = atypeFactory.getQualifierHierarchy();
AnnotationMirror invariantAnno = atypeFactory.getFieldInvariantAnnotation();
// Remember fields that have the 'invariant' annotation in the store.
if (je instanceof FieldAccess) {
FieldAccess fieldAccess = (FieldAccess) je;
if (!fieldValues.containsKey(je)) {
Set<AnnotationMirror> declaredAnnos = atypeFactory.getAnnotatedType(fieldAccess.getField()).getAnnotations();
if (AnnotationUtils.containsSame(declaredAnnos, invariantAnno)) {
if (!invariantFields.containsKey(fieldAccess)) {
invariantFields.put(fieldAccess, analysis.createSingleAnnotationValue(invariantAnno, je.getType()));
}
}
}
}
super.insertValue(je, value, permitNondeterministic);
for (AnnotationMirror a : value.getAnnotations()) {
if (qualifierHierarchy.isSubtype(a, invariantAnno)) {
if (je instanceof FieldAccess) {
FieldAccess fa = (FieldAccess) je;
if (fa.getReceiver() instanceof ThisReference || fa.getReceiver() instanceof ClassName) {
addInitializedField(fa.getField());
}
}
}
}
}
use of org.checkerframework.dataflow.expression.ThisReference in project checker-framework by typetools.
the class LockStore method insertLockPossiblyHeld.
/*
* Insert an annotation exactly, without regard to whether an annotation was already present.
* This is only done for @LockPossiblyHeld. This is not sound for other type qualifiers.
*/
public void insertLockPossiblyHeld(JavaExpression je) {
if (je.containsUnknown()) {
// Expressions containing unknown expressions are not stored.
return;
}
if (je instanceof LocalVariable) {
LocalVariable localVar = (LocalVariable) je;
CFValue current = localVariableValues.get(localVar);
CFValue value = changeLockAnnoToTop(je, current);
if (value != null) {
localVariableValues.put(localVar, value);
}
} else if (je instanceof FieldAccess) {
FieldAccess fieldAcc = (FieldAccess) je;
CFValue current = fieldValues.get(fieldAcc);
CFValue value = changeLockAnnoToTop(je, current);
if (value != null) {
fieldValues.put(fieldAcc, value);
}
} else if (je instanceof MethodCall) {
MethodCall method = (MethodCall) je;
CFValue current = methodValues.get(method);
CFValue value = changeLockAnnoToTop(je, current);
if (value != null) {
methodValues.put(method, value);
}
} else if (je instanceof ArrayAccess) {
ArrayAccess arrayAccess = (ArrayAccess) je;
CFValue current = arrayValues.get(arrayAccess);
CFValue value = changeLockAnnoToTop(je, current);
if (value != null) {
arrayValues.put(arrayAccess, value);
}
} else if (je instanceof ThisReference) {
thisValue = changeLockAnnoToTop(je, thisValue);
} else if (je instanceof ClassName) {
ClassName className = (ClassName) je;
CFValue current = classValues.get(className);
CFValue value = changeLockAnnoToTop(je, current);
if (value != null) {
classValues.put(className, value);
}
} else {
// No other types of expressions need to be stored.
}
}
Aggregations