Search in sources :

Example 1 with Equalities

use of org.checkerframework.framework.util.typeinference.solver.TargetConstraints.Equalities in project checker-framework by typetools.

the class ConstraintMap method addTargetEquality.

/**
 * Add a constraint indicating that the equivalent is equal to target in the given qualifier
 * hierarchies
 */
public void addTargetEquality(final TypeVariable target, final TypeVariable equivalent, AnnotationMirrorSet hierarchies) {
    final Equalities equalities = targetToRecords.get(target).equalities;
    final AnnotationMirrorSet equivalentTops = equalities.targets.get(equivalent);
    if (equivalentTops == null) {
        equalities.targets.put(equivalent, new AnnotationMirrorSet(hierarchies));
    } else {
        equivalentTops.addAll(hierarchies);
    }
}
Also used : Equalities(org.checkerframework.framework.util.typeinference.solver.TargetConstraints.Equalities) AnnotationMirrorSet(org.checkerframework.framework.util.AnnotationMirrorSet)

Example 2 with Equalities

use of org.checkerframework.framework.util.typeinference.solver.TargetConstraints.Equalities in project checker-framework by typetools.

the class EqualitiesSolver method solveEqualities.

/**
 * For each target, if there is one or more equality constraints involving concrete types that
 * lets us infer a primary annotation in all qualifier hierarchies then infer a concrete type
 * argument. else if there is one or more equality constraints involving other targets that lets
 * us infer a primary annotation in all qualifier hierarchies then infer that type argument is
 * the other type argument
 *
 * <p>if we have inferred either a concrete type or another target as type argument rewrite all
 * of the constraints for the current target to instead use the inferred type/target
 *
 * <p>We do this iteratively until NO new inferred type argument is found
 *
 * @param targets the list of type parameters for which we are inferring type arguments
 * @param constraintMap the set of constraints over the set of targets
 * @return a Map( {@code target &rArr; inferred type or target })
 */
public InferenceResult solveEqualities(Set<TypeVariable> targets, ConstraintMap constraintMap, AnnotatedTypeFactory typeFactory) {
    final InferenceResult solution = new InferenceResult();
    do {
        dirty = false;
        for (TypeVariable target : targets) {
            if (solution.containsKey(target)) {
                continue;
            }
            Equalities equalities = constraintMap.getConstraints(target).equalities;
            InferredValue inferred = mergeConstraints(target, equalities, solution, constraintMap, typeFactory);
            if (inferred != null) {
                if (inferred instanceof InferredType) {
                    rewriteWithInferredType(target, ((InferredType) inferred).type, constraintMap);
                } else {
                    rewriteWithInferredTarget(target, ((InferredTarget) inferred).target, constraintMap, typeFactory);
                }
                solution.put(target, inferred);
            }
        }
    } while (dirty);
    solution.resolveChainedTargets();
    return solution;
}
Also used : InferredType(org.checkerframework.framework.util.typeinference.solver.InferredValue.InferredType) AnnotatedTypeVariable(org.checkerframework.framework.type.AnnotatedTypeMirror.AnnotatedTypeVariable) TypeVariable(javax.lang.model.type.TypeVariable) Equalities(org.checkerframework.framework.util.typeinference.solver.TargetConstraints.Equalities)

Example 3 with Equalities

use of org.checkerframework.framework.util.typeinference.solver.TargetConstraints.Equalities in project checker-framework by typetools.

the class ConstraintMap method addTypeEqualities.

/**
 * Add a constraint indicating that target is equal to type in the given hierarchies
 *
 * @param hierarchies a set of TOP annotations
 */
public void addTypeEqualities(TypeVariable target, AnnotatedTypeMirror type, AnnotationMirrorSet hierarchies) {
    final Equalities equalities = targetToRecords.get(target).equalities;
    final AnnotationMirrorSet equalityTops = equalities.types.get(type);
    if (equalityTops == null) {
        equalities.types.put(type, new AnnotationMirrorSet(hierarchies));
    } else {
        equalityTops.addAll(hierarchies);
    }
}
Also used : Equalities(org.checkerframework.framework.util.typeinference.solver.TargetConstraints.Equalities) AnnotationMirrorSet(org.checkerframework.framework.util.AnnotationMirrorSet)

Example 4 with Equalities

use of org.checkerframework.framework.util.typeinference.solver.TargetConstraints.Equalities in project checker-framework by typetools.

the class SupertypesSolver method mergeLubTypeWithEqualities.

/**
 * We previously found a type that is equal to target but not in all hierarchies. Use the
 * primary annotations from the lub type to fill in the missing annotations in this type. Use
 * that type as the inferred argument.
 *
 * <p>If we failed to infer any annotation for a given hierarchy, either previously from
 * equalities or from the lub, return null.
 */
protected InferredType mergeLubTypeWithEqualities(final TypeVariable target, final AnnotatedTypeMirror lub, final ConstraintMap constraintMap, final AnnotatedTypeFactory typeFactory) {
    final Equalities equalities = constraintMap.getConstraints(target).equalities;
    final AnnotationMirrorSet tops = new AnnotationMirrorSet(typeFactory.getQualifierHierarchy().getTopAnnotations());
    if (!equalities.types.isEmpty()) {
        // there should be only one equality type if any at this point
        final Entry<AnnotatedTypeMirror, AnnotationMirrorSet> eqEntry = equalities.types.entrySet().iterator().next();
        final AnnotatedTypeMirror equalityType = eqEntry.getKey();
        final AnnotationMirrorSet equalityAnnos = eqEntry.getValue();
        boolean failed = false;
        for (final AnnotationMirror top : tops) {
            if (!equalityAnnos.contains(top)) {
                final AnnotationMirror lubAnno = lub.getAnnotationInHierarchy(top);
                if (lubAnno == null) {
                    // unannotated then "NO ANNOTATION" is the correct choice.
                    if (lub.getKind() == TypeKind.TYPEVAR && equalityType.getUnderlyingType().equals(lub.getUnderlyingType())) {
                        equalityAnnos.add(top);
                    } else {
                        failed = true;
                    }
                } else {
                    equalityType.replaceAnnotation(lubAnno);
                    equalityAnnos.add(top);
                }
            }
        }
        if (!failed) {
            return new InferredType(equalityType);
        }
    }
    return new InferredType(lub);
}
Also used : AnnotationMirror(javax.lang.model.element.AnnotationMirror) InferredType(org.checkerframework.framework.util.typeinference.solver.InferredValue.InferredType) Equalities(org.checkerframework.framework.util.typeinference.solver.TargetConstraints.Equalities) AnnotationMirrorSet(org.checkerframework.framework.util.AnnotationMirrorSet) AnnotatedTypeMirror(org.checkerframework.framework.type.AnnotatedTypeMirror)

Example 5 with Equalities

use of org.checkerframework.framework.util.typeinference.solver.TargetConstraints.Equalities in project checker-framework by typetools.

the class SupertypesSolver method mergeLubAnnosWithEqualities.

/**
 * We previously found a type that is equal to target but not in all hierarchies. Use the
 * primary annotations from the lub annos to fill in the missing annotations in this type. Use
 * that type as the inferred argument.
 *
 * <p>If we failed to infer any annotation for a given hierarchy, either previously from
 * equalities or from the lub, return null.
 */
protected InferredType mergeLubAnnosWithEqualities(final TypeVariable target, final AnnotationMirrorMap<AnnotationMirror> lubAnnos, final ConstraintMap constraintMap, final AnnotatedTypeFactory typeFactory) {
    final Equalities equalities = constraintMap.getConstraints(target).equalities;
    final AnnotationMirrorSet tops = new AnnotationMirrorSet(typeFactory.getQualifierHierarchy().getTopAnnotations());
    if (!equalities.types.isEmpty()) {
        // there should be only equality type if any at this point
        final Entry<AnnotatedTypeMirror, AnnotationMirrorSet> eqEntry = equalities.types.entrySet().iterator().next();
        final AnnotatedTypeMirror equalityType = eqEntry.getKey();
        final AnnotationMirrorSet equalityAnnos = eqEntry.getValue();
        boolean failed = false;
        for (final AnnotationMirror top : tops) {
            if (!equalityAnnos.contains(top)) {
                final AnnotationMirror lubAnno = lubAnnos.get(top);
                if (lubAnno == null) {
                    failed = true;
                } else {
                    equalityType.replaceAnnotation(lubAnno);
                    equalityAnnos.add(top);
                }
            }
        }
        if (!failed) {
            return new InferredType(equalityType);
        }
    }
    return null;
}
Also used : AnnotationMirror(javax.lang.model.element.AnnotationMirror) InferredType(org.checkerframework.framework.util.typeinference.solver.InferredValue.InferredType) Equalities(org.checkerframework.framework.util.typeinference.solver.TargetConstraints.Equalities) AnnotationMirrorSet(org.checkerframework.framework.util.AnnotationMirrorSet) AnnotatedTypeMirror(org.checkerframework.framework.type.AnnotatedTypeMirror)

Aggregations

Equalities (org.checkerframework.framework.util.typeinference.solver.TargetConstraints.Equalities)5 AnnotationMirrorSet (org.checkerframework.framework.util.AnnotationMirrorSet)4 InferredType (org.checkerframework.framework.util.typeinference.solver.InferredValue.InferredType)3 AnnotationMirror (javax.lang.model.element.AnnotationMirror)2 AnnotatedTypeMirror (org.checkerframework.framework.type.AnnotatedTypeMirror)2 TypeVariable (javax.lang.model.type.TypeVariable)1 AnnotatedTypeVariable (org.checkerframework.framework.type.AnnotatedTypeMirror.AnnotatedTypeVariable)1