Skip to content

Commit 10fa811

Browse files
committed
[CSStep] Conjunctions representing closures affect declaration context
While solving a conjunction that represents a (multi-statement) closure constraint system should use such closure as its declaration context, otherwise member lookup would produce incorrect results.
1 parent 598b850 commit 10fa811

File tree

1 file changed

+13
-2
lines changed

1 file changed

+13
-2
lines changed

lib/Sema/CSStep.h

Lines changed: 13 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -26,6 +26,7 @@
2626
#include "llvm/ADT/Optional.h"
2727
#include "llvm/ADT/STLExtras.h"
2828
#include "llvm/ADT/SmallVector.h"
29+
#include "llvm/Support/SaveAndRestore.h"
2930
#include "llvm/Support/raw_ostream.h"
3031
#include <memory>
3132

@@ -772,6 +773,8 @@ class ConjunctionStep : public BindingStep<ConjunctionElementProducer> {
772773
class SolverSnapshot {
773774
ConstraintSystem &CS;
774775

776+
Optional<llvm::SaveAndRestore<DeclContext *>> DC = None;
777+
775778
llvm::SetVector<TypeVariableType *> TypeVars;
776779
ConstraintList Constraints;
777780

@@ -782,8 +785,15 @@ class ConjunctionStep : public BindingStep<ConjunctionElementProducer> {
782785
std::unique_ptr<Scope> IsolationScope = nullptr;
783786

784787
public:
785-
SolverSnapshot(ConstraintSystem &cs)
788+
SolverSnapshot(ConstraintSystem &cs, Constraint *conjunction)
786789
: CS(cs), TypeVars(std::move(cs.TypeVariables)) {
790+
auto *locator = conjunction->getLocator();
791+
// If this conjunction represents a closure, we need to
792+
// switch declaration context over to it.
793+
if (locator->directlyAt<ClosureExpr>()) {
794+
DC.emplace(CS.DC, castToExpr<ClosureExpr>(locator->getAnchor()));
795+
}
796+
787797
auto &CG = CS.getConstraintGraph();
788798
// Remove all of the current inactive constraints.
789799
Constraints.splice(Constraints.end(), CS.InactiveConstraints);
@@ -827,6 +837,7 @@ class ConjunctionStep : public BindingStep<ConjunctionElementProducer> {
827837

828838
private:
829839
void restore() {
840+
DC.reset();
830841
CS.TypeVariables = std::move(TypeVars);
831842
CS.InactiveConstraints.splice(CS.InactiveConstraints.end(), Constraints);
832843
}
@@ -881,7 +892,7 @@ class ConjunctionStep : public BindingStep<ConjunctionElementProducer> {
881892

882893
// Make a snapshot of the constraint system state before conjunction.
883894
if (conjunction->isIsolated())
884-
Snapshot.emplace(cs);
895+
Snapshot.emplace(cs, conjunction);
885896
}
886897

887898
~ConjunctionStep() override {

0 commit comments

Comments
 (0)