use of org.checkerframework.framework.util.typeinference.solver.TargetConstraints.Subtypes in project checker-framework by typetools.
the class ConstraintMap method addTargetSubtype.
/**
* Add a constraint indicating that target is a subtype of supertype in the given qualifier
* hierarchies
*
* @param hierarchies a set of TOP annotations
*/
public void addTargetSubtype(final TypeVariable target, final TypeVariable supertype, AnnotationMirrorSet hierarchies) {
final Subtypes subtypes = targetToRecords.get(target).subtypes;
final AnnotationMirrorSet subtypesTops = subtypes.targets.get(supertype);
if (subtypesTops == null) {
subtypes.targets.put(supertype, new AnnotationMirrorSet(hierarchies));
} else {
subtypesTops.addAll(hierarchies);
}
}
use of org.checkerframework.framework.util.typeinference.solver.TargetConstraints.Subtypes in project checker-framework by typetools.
the class ConstraintMap method addTypeSubtype.
/**
* Add a constraint indicating that target is a subtype of supertype in the given qualifier
* hierarchies
*
* @param hierarchies a set of TOP annotations
*/
public void addTypeSubtype(final TypeVariable target, final AnnotatedTypeMirror supertype, AnnotationMirrorSet hierarchies) {
final Subtypes subtypes = targetToRecords.get(target).subtypes;
final AnnotationMirrorSet subtypesTops = subtypes.types.get(supertype);
if (subtypesTops == null) {
subtypes.types.put(supertype, new AnnotationMirrorSet(hierarchies));
} else {
subtypesTops.addAll(hierarchies);
}
}
use of org.checkerframework.framework.util.typeinference.solver.TargetConstraints.Subtypes in project checker-framework by typetools.
the class ConstraintMap method addPrimarySubtypes.
/**
* Add a constraint indicating that target's primary annotations are subtypes of the given
* annotations
*/
public void addPrimarySubtypes(final TypeVariable target, QualifierHierarchy qualifierHierarchy, final AnnotationMirrorSet annos) {
final Subtypes subtypes = targetToRecords.get(target).subtypes;
for (final AnnotationMirror anno : annos) {
final AnnotationMirror top = qualifierHierarchy.getTopAnnotation(anno);
AnnotationMirrorSet entries = subtypes.primaries.get(top);
if (entries == null) {
entries = new AnnotationMirrorSet();
subtypes.primaries.put(top, entries);
}
entries.add(anno);
}
}
use of org.checkerframework.framework.util.typeinference.solver.TargetConstraints.Subtypes in project checker-framework by typetools.
the class SubtypesSolver method glbSubtypes.
public InferenceResult glbSubtypes(final Set<TypeVariable> remainingTargets, final ConstraintMap constraints, final AnnotatedTypeFactory typeFactory) {
final InferenceResult inferenceResult = new InferenceResult();
final QualifierHierarchy qualifierHierarchy = typeFactory.getQualifierHierarchy();
final Types types = typeFactory.getProcessingEnv().getTypeUtils();
List<TypeVariable> targetsSubtypesLast = new ArrayList<>(remainingTargets);
// If we have two type variables <A, A extends B> order them A then B
// this is required because we will use the fact that B must be below A
// when determining the glb of B
Collections.sort(targetsSubtypesLast, new Comparator<TypeVariable>() {
@Override
public int compare(TypeVariable o1, TypeVariable o2) {
if (types.isSubtype(o1, o2)) {
return 1;
} else if (types.isSubtype(o2, o1)) {
return -1;
}
return 0;
}
});
for (final TypeVariable target : targetsSubtypesLast) {
Subtypes subtypes = constraints.getConstraints(target).subtypes;
if (subtypes.types.isEmpty()) {
continue;
}
propagatePreviousGlbs(subtypes, inferenceResult, subtypes.types);
// if the subtypes size is only 1 then we need not do any GLBing on the underlying types
// but we may have primary annotations that need to be GLBed
AnnotationMirrorMap<AnnotationMirrorSet> primaries = subtypes.primaries;
if (subtypes.types.size() == 1) {
final Entry<AnnotatedTypeMirror, AnnotationMirrorSet> entry = subtypes.types.entrySet().iterator().next();
AnnotatedTypeMirror supertype = entry.getKey().deepCopy();
for (AnnotationMirror top : entry.getValue()) {
final AnnotationMirrorSet superAnnos = primaries.get(top);
// if it is null we're just going to use the anno already on supertype
if (superAnnos != null) {
final AnnotationMirror supertypeAnno = supertype.getAnnotationInHierarchy(top);
superAnnos.add(supertypeAnno);
}
}
if (!primaries.isEmpty()) {
for (AnnotationMirror top : qualifierHierarchy.getTopAnnotations()) {
final AnnotationMirror glb = greatestLowerBound(subtypes.primaries.get(top), qualifierHierarchy);
supertype.replaceAnnotation(glb);
}
}
inferenceResult.put(target, new InferredType(supertype));
} else {
// GLB all of the types than combine this with the GLB of primary annotation
// constraints
final AnnotatedTypeMirror glbType = GlbUtil.glbAll(subtypes.types, typeFactory);
if (glbType != null) {
if (!primaries.isEmpty()) {
for (AnnotationMirror top : qualifierHierarchy.getTopAnnotations()) {
final AnnotationMirror glb = greatestLowerBound(subtypes.primaries.get(top), qualifierHierarchy);
final AnnotationMirror currentAnno = glbType.getAnnotationInHierarchy(top);
if (currentAnno == null) {
glbType.addAnnotation(glb);
} else if (glb != null) {
glbType.replaceAnnotation(qualifierHierarchy.greatestLowerBound(glb, currentAnno));
}
}
}
inferenceResult.put(target, new InferredType(glbType));
}
}
}
return inferenceResult;
}
Aggregations