Skip to content

Commit 6d8b55a

Browse files
committed
Sema: Split up gatherConstraints() into gatherAllConstraints() and gatherNearbyConstraints()
The two GatherKinds no longer share any implementation, so there's no point keeping the logic together. Doing this also allows removing the acceptConstraintFn from gatherAllConstraints(), which further simplifies depthFirstSearch().
1 parent 2500c83 commit 6d8b55a

File tree

7 files changed

+37
-62
lines changed

7 files changed

+37
-62
lines changed

include/swift/Sema/ConstraintGraph.h

+10-17
Original file line numberDiff line numberDiff line change
@@ -295,25 +295,18 @@ class ConstraintGraph {
295295
/// to a type variable.
296296
void introduceToInference(TypeVariableType *typeVar, Type fixedType);
297297

298-
/// Describes which constraints \c gatherConstraints should gather.
299-
enum class GatheringKind {
300-
/// Gather constraints associated with all of the variables within the
301-
/// same equivalence class as the given type variable, as well as its
302-
/// immediate fixed bindings.
303-
EquivalenceClass,
304-
/// Gather all constraints that mention this type variable or type variables
305-
/// that it is a fixed binding of. Unlike EquivalenceClass, this looks
306-
/// through transitive fixed bindings. This can be used to find all the
307-
/// constraints that may be affected when binding a type variable.
308-
AllMentions,
309-
};
298+
/// Gather constraints associated with all of the variables within the
299+
/// same equivalence class as the given type variable, as well as its
300+
/// immediate fixed bindings.
301+
llvm::TinyPtrVector<Constraint *>
302+
gatherAllConstraints(TypeVariableType *typeVar);
310303

311-
/// Gather the set of constraints that involve the given type variable,
312-
/// i.e., those constraints that will be affected when the type variable
313-
/// gets merged or bound to a fixed type.
304+
/// Gather all constraints that mention this type variable or type variables
305+
/// that it is a fixed binding of. Unlike EquivalenceClass, this looks
306+
/// through transitive fixed bindings. This can be used to find all the
307+
/// constraints that may be affected when binding a type variable.
314308
llvm::TinyPtrVector<Constraint *>
315-
gatherConstraints(TypeVariableType *typeVar,
316-
GatheringKind kind,
309+
gatherNearbyConstraints(TypeVariableType *typeVar,
317310
llvm::function_ref<bool(Constraint *)> acceptConstraint =
318311
[](Constraint *constraint) { return true; });
319312

lib/Sema/CSGen.cpp

+2-2
Original file line numberDiff line numberDiff line change
@@ -400,8 +400,8 @@ namespace {
400400

401401
llvm::SmallSetVector<ProtocolDecl *, 2> literalProtos;
402402
if (auto argTypeVar = argTy->getAs<TypeVariableType>()) {
403-
auto constraints = CS.getConstraintGraph().gatherConstraints(
404-
argTypeVar, ConstraintGraph::GatheringKind::EquivalenceClass,
403+
auto constraints = CS.getConstraintGraph().gatherNearbyConstraints(
404+
argTypeVar,
405405
[](Constraint *constraint) {
406406
return constraint->getKind() == ConstraintKind::LiteralConformsTo;
407407
});

lib/Sema/CSSimplify.cpp

+2-2
Original file line numberDiff line numberDiff line change
@@ -15953,8 +15953,8 @@ ConstraintSystem::addKeyPathApplicationRootConstraint(Type root, ConstraintLocat
1595315953
if (!typeVar)
1595415954
return;
1595515955

15956-
auto constraints = CG.gatherConstraints(
15957-
typeVar, ConstraintGraph::GatheringKind::EquivalenceClass,
15956+
auto constraints = CG.gatherNearbyConstraints(
15957+
typeVar,
1595815958
[&keyPathExpr](Constraint *constraint) -> bool {
1595915959
if (constraint->getKind() != ConstraintKind::KeyPath)
1596015960
return false;

lib/Sema/CSSolver.cpp

+5-6
Original file line numberDiff line numberDiff line change
@@ -1876,8 +1876,8 @@ static Constraint *selectBestBindingDisjunction(
18761876
if (!firstBindDisjunction)
18771877
firstBindDisjunction = disjunction;
18781878

1879-
auto constraints = cs.getConstraintGraph().gatherConstraints(
1880-
typeVar, ConstraintGraph::GatheringKind::EquivalenceClass,
1879+
auto constraints = cs.getConstraintGraph().gatherNearbyConstraints(
1880+
typeVar,
18811881
[](Constraint *constraint) {
18821882
return constraint->getKind() == ConstraintKind::Conversion;
18831883
});
@@ -1906,8 +1906,8 @@ ConstraintSystem::findConstraintThroughOptionals(
19061906
while (visitedVars.insert(rep).second) {
19071907
// Look for a disjunction that binds this type variable to an overload set.
19081908
TypeVariableType *optionalObjectTypeVar = nullptr;
1909-
auto constraints = getConstraintGraph().gatherConstraints(
1910-
rep, ConstraintGraph::GatheringKind::EquivalenceClass,
1909+
auto constraints = getConstraintGraph().gatherNearbyConstraints(
1910+
rep,
19111911
[&](Constraint *match) {
19121912
// If we have an "optional object of" constraint, we may need to
19131913
// look through it to find the constraint we're looking for.
@@ -2549,9 +2549,8 @@ void DisjunctionChoice::propagateConversionInfo(ConstraintSystem &cs) const {
25492549
}
25502550
}
25512551

2552-
auto constraints = cs.CG.gatherConstraints(
2552+
auto constraints = cs.CG.gatherNearbyConstraints(
25532553
typeVar,
2554-
ConstraintGraph::GatheringKind::EquivalenceClass,
25552554
[](Constraint *constraint) -> bool {
25562555
switch (constraint->getKind()) {
25572556
case ConstraintKind::Conversion:

lib/Sema/ConstraintGraph.cpp

+15-31
Original file line numberDiff line numberDiff line change
@@ -545,18 +545,11 @@ void ConstraintGraph::retractBindings(TypeVariableType *typeVar,
545545

546546
#pragma mark Algorithms
547547

548-
/// Perform a depth-first search.
549-
///
550-
/// \param cg The constraint graph.
551-
/// \param typeVar The type variable we're searching from.
552-
/// \param visitConstraint Called before considering a constraint.
553-
/// \param visitedConstraints Set of already-visited constraints, used
554-
/// internally to avoid duplicated work.
555548
static void depthFirstSearch(
556549
ConstraintGraph &cg,
557550
TypeVariableType *typeVar,
558-
llvm::function_ref<void(Constraint *)> visitConstraint,
559551
llvm::SmallPtrSet<TypeVariableType *, 4> &typeVars,
552+
llvm::TinyPtrVector<Constraint *> &constraints,
560553
llvm::SmallPtrSet<Constraint *, 8> &visitedConstraints) {
561554
// If we're not looking at this type variable right now because we're
562555
// solving a conjunction element, don't consider its adjacencies.
@@ -570,11 +563,8 @@ static void depthFirstSearch(
570563
// Local function to visit adjacent type variables.
571564
auto visitAdjacencies = [&](ArrayRef<TypeVariableType *> adjTypeVars) {
572565
for (auto adj : adjTypeVars) {
573-
if (adj == typeVar)
574-
continue;
575-
576-
// Recurse into this node.
577-
depthFirstSearch(cg, adj, visitConstraint, typeVars, visitedConstraints);
566+
if (adj != typeVar)
567+
depthFirstSearch(cg, adj, typeVars, constraints, visitedConstraints);
578568
}
579569
};
580570

@@ -585,7 +575,7 @@ static void depthFirstSearch(
585575
if (!visitedConstraints.insert(constraint).second)
586576
continue;
587577

588-
visitConstraint(constraint);
578+
constraints.push_back(constraint);
589579
}
590580

591581
// Visit all of the other nodes in the equivalence class.
@@ -604,28 +594,22 @@ static void depthFirstSearch(
604594
visitAdjacencies(node.getReferencedVars());
605595
}
606596

607-
llvm::TinyPtrVector<Constraint *> ConstraintGraph::gatherConstraints(
608-
TypeVariableType *typeVar, GatheringKind kind,
609-
llvm::function_ref<bool(Constraint *)> acceptConstraintFn) {
597+
llvm::TinyPtrVector<Constraint *> ConstraintGraph::gatherAllConstraints(
598+
TypeVariableType *typeVar) {
610599
llvm::TinyPtrVector<Constraint *> constraints;
611600
llvm::SmallPtrSet<TypeVariableType *, 4> typeVars;
612601
llvm::SmallPtrSet<Constraint *, 8> visitedConstraints;
613602

614-
if (kind == GatheringKind::AllMentions) {
615-
// If we've been asked for "all mentions" of a type variable, search for
616-
// constraints involving both it and its fixed bindings.
617-
depthFirstSearch(
618-
*this, typeVar,
619-
[&](Constraint *constraint) {
620-
if (acceptConstraintFn(constraint))
621-
constraints.push_back(constraint);
622-
},
623-
typeVars, visitedConstraints);
624-
return constraints;
625-
}
603+
depthFirstSearch(*this, typeVar, typeVars, constraints, visitedConstraints);
604+
return constraints;
605+
}
626606

627-
// Otherwise only search in the type var's equivalence class and immediate
628-
// fixed bindings.
607+
llvm::TinyPtrVector<Constraint *> ConstraintGraph::gatherNearbyConstraints(
608+
TypeVariableType *typeVar,
609+
llvm::function_ref<bool(Constraint *)> acceptConstraintFn) {
610+
llvm::TinyPtrVector<Constraint *> constraints;
611+
llvm::SmallPtrSet<TypeVariableType *, 4> typeVars;
612+
llvm::SmallPtrSet<Constraint *, 8> visitedConstraints;
629613

630614
// Local function to add constraints.
631615
auto addTypeVarConstraints = [&](TypeVariableType *adjTypeVar) {

lib/Sema/ConstraintSystem.cpp

+1-2
Original file line numberDiff line numberDiff line change
@@ -267,8 +267,7 @@ void ConstraintSystem::assignFixedType(TypeVariableType *typeVar, Type type,
267267
void ConstraintSystem::addTypeVariableConstraintsToWorkList(
268268
TypeVariableType *typeVar) {
269269
// Activate the constraints affected by a change to this type variable.
270-
auto gatheringKind = ConstraintGraph::GatheringKind::AllMentions;
271-
for (auto *constraint : CG.gatherConstraints(typeVar, gatheringKind))
270+
for (auto *constraint : CG.gatherAllConstraints(typeVar))
272271
if (!constraint->isActive())
273272
activateConstraint(constraint);
274273
}

lib/Sema/TypeOfReference.cpp

+2-2
Original file line numberDiff line numberDiff line change
@@ -2058,8 +2058,8 @@ void ConstraintSystem::bindOverloadType(
20582058
increaseScore(SK_KeyPathSubscript, locator);
20592059

20602060
auto boundTypeVar = boundType->castTo<TypeVariableType>();
2061-
auto constraints = getConstraintGraph().gatherConstraints(
2062-
boundTypeVar, ConstraintGraph::GatheringKind::EquivalenceClass,
2061+
auto constraints = getConstraintGraph().gatherNearbyConstraints(
2062+
boundTypeVar,
20632063
[](Constraint *constraint) {
20642064
return constraint->getKind() == ConstraintKind::ApplicableFunction;
20652065
});

0 commit comments

Comments
 (0)