Coverage Report

Created: 2021-06-15 06:44

/Users/buildslave/jenkins/workspace/coverage/llvm-project/clang/lib/Sema/SemaConcept.cpp
Line
Count
Source (jump to first uncovered line)
1
//===-- SemaConcept.cpp - Semantic Analysis for Constraints and Concepts --===//
2
//
3
//                     The LLVM Compiler Infrastructure
4
//
5
// This file is distributed under the University of Illinois Open Source
6
// License. See LICENSE.TXT for details.
7
//
8
//===----------------------------------------------------------------------===//
9
//
10
//  This file implements semantic analysis for C++ constraints and concepts.
11
//
12
//===----------------------------------------------------------------------===//
13
14
#include "clang/Sema/SemaConcept.h"
15
#include "clang/Sema/Sema.h"
16
#include "clang/Sema/SemaInternal.h"
17
#include "clang/Sema/SemaDiagnostic.h"
18
#include "clang/Sema/TemplateDeduction.h"
19
#include "clang/Sema/Template.h"
20
#include "clang/Sema/Overload.h"
21
#include "clang/Sema/Initialization.h"
22
#include "clang/Sema/SemaInternal.h"
23
#include "clang/AST/ExprConcepts.h"
24
#include "clang/AST/RecursiveASTVisitor.h"
25
#include "clang/Basic/OperatorPrecedence.h"
26
#include "llvm/ADT/DenseMap.h"
27
#include "llvm/ADT/PointerUnion.h"
28
#include "llvm/ADT/StringExtras.h"
29
30
using namespace clang;
31
using namespace sema;
32
33
namespace {
34
class LogicalBinOp {
35
  OverloadedOperatorKind Op = OO_None;
36
  const Expr *LHS = nullptr;
37
  const Expr *RHS = nullptr;
38
39
public:
40
3.49k
  LogicalBinOp(const Expr *E) {
41
3.49k
    if (auto *BO = dyn_cast<BinaryOperator>(E)) {
42
1.21k
      Op = BinaryOperator::getOverloadedOperator(BO->getOpcode());
43
1.21k
      LHS = BO->getLHS();
44
1.21k
      RHS = BO->getRHS();
45
2.28k
    } else if (auto *OO = dyn_cast<CXXOperatorCallExpr>(E)) {
46
7
      Op = OO->getOperator();
47
7
      LHS = OO->getArg(0);
48
7
      RHS = OO->getArg(1);
49
7
    }
50
3.49k
  }
51
52
3.67k
  bool isAnd() const { return Op == OO_AmpAmp; }
53
3.35k
  bool isOr() const { return Op == OO_PipePipe; }
54
3.49k
  explicit operator bool() const { return isAnd() || 
isOr()3.21k
; }
55
56
358
  const Expr *getLHS() const { return LHS; }
57
305
  const Expr *getRHS() const { return RHS; }
58
};
59
}
60
61
bool Sema::CheckConstraintExpression(const Expr *ConstraintExpression,
62
                                     Token NextToken, bool *PossibleNonPrimary,
63
2.14k
                                     bool IsTrailingRequiresClause) {
64
  // C++2a [temp.constr.atomic]p1
65
  // ..E shall be a constant expression of type bool.
66
67
2.14k
  ConstraintExpression = ConstraintExpression->IgnoreParenImpCasts();
68
69
2.14k
  if (LogicalBinOp BO = ConstraintExpression) {
70
164
    return CheckConstraintExpression(BO.getLHS(), NextToken,
71
164
                                     PossibleNonPrimary) &&
72
164
           CheckConstraintExpression(BO.getRHS(), NextToken,
73
159
                                     PossibleNonPrimary);
74
1.98k
  } else if (auto *C = dyn_cast<ExprWithCleanups>(ConstraintExpression))
75
0
    return CheckConstraintExpression(C->getSubExpr(), NextToken,
76
0
                                     PossibleNonPrimary);
77
78
1.98k
  QualType Type = ConstraintExpression->getType();
79
80
1.98k
  auto CheckForNonPrimary = [&] {
81
145
    if (PossibleNonPrimary)
82
82
      *PossibleNonPrimary =
83
          // We have the following case:
84
          // template<typename> requires func(0) struct S { };
85
          // The user probably isn't aware of the parentheses required around
86
          // the function call, and we're only going to parse 'func' as the
87
          // primary-expression, and complain that it is of non-bool type.
88
82
          (NextToken.is(tok::l_paren) &&
89
82
           
(12
IsTrailingRequiresClause12
||
90
12
            
(8
Type->isDependentType()8
&&
91
8
             
isa<UnresolvedLookupExpr>(ConstraintExpression)4
) ||
92
12
            
Type->isFunctionType()4
||
93
12
            
Type->isSpecificBuiltinType(BuiltinType::Overload)4
)) ||
94
          // We have the following case:
95
          // template<typename T> requires size_<T> == 0 struct S { };
96
          // The user probably isn't aware of the parentheses required around
97
          // the binary operator, and we're only going to parse 'func' as the
98
          // first operand, and complain that it is of non-bool type.
99
82
          getBinOpPrecedence(NextToken.getKind(),
100
72
                             /*GreaterThanIsOperator=*/true,
101
72
                             getLangOpts().CPlusPlus11) > prec::LogicalAnd;
102
145
  };
103
104
  // An atomic constraint!
105
1.98k
  if (ConstraintExpression->isTypeDependent()) {
106
129
    CheckForNonPrimary();
107
129
    return true;
108
129
  }
109
110
1.85k
  if (!Context.hasSameUnqualifiedType(Type, Context.BoolTy)) {
111
16
    Diag(ConstraintExpression->getExprLoc(),
112
16
         diag::err_non_bool_atomic_constraint) << Type
113
16
        << ConstraintExpression->getSourceRange();
114
16
    CheckForNonPrimary();
115
16
    return false;
116
16
  }
117
118
1.83k
  if (PossibleNonPrimary)
119
440
      *PossibleNonPrimary = false;
120
1.83k
  return true;
121
1.85k
}
122
123
template <typename AtomicEvaluator>
124
static bool
125
calculateConstraintSatisfaction(Sema &S, const Expr *ConstraintExpr,
126
                                ConstraintSatisfaction &Satisfaction,
127
1.11k
                                AtomicEvaluator &&Evaluator) {
128
1.11k
  ConstraintExpr = ConstraintExpr->IgnoreParenImpCasts();
129
130
1.11k
  if (LogicalBinOp BO = ConstraintExpr) {
131
142
    if (calculateConstraintSatisfaction(S, BO.getLHS(), Satisfaction,
132
142
                                        Evaluator))
133
2
      return true;
134
135
140
    bool IsLHSSatisfied = Satisfaction.IsSatisfied;
136
137
140
    if (BO.isOr() && 
IsLHSSatisfied32
)
138
      // [temp.constr.op] p3
139
      //    A disjunction is a constraint taking two operands. To determine if
140
      //    a disjunction is satisfied, the satisfaction of the first operand
141
      //    is checked. If that is satisfied, the disjunction is satisfied.
142
      //    Otherwise, the disjunction is satisfied if and only if the second
143
      //    operand is satisfied.
144
15
      return false;
145
146
125
    if (BO.isAnd() && 
!IsLHSSatisfied108
)
147
      // [temp.constr.op] p2
148
      //    A conjunction is a constraint taking two operands. To determine if
149
      //    a conjunction is satisfied, the satisfaction of the first operand
150
      //    is checked. If that is not satisfied, the conjunction is not
151
      //    satisfied. Otherwise, the conjunction is satisfied if and only if
152
      //    the second operand is satisfied.
153
30
      return false;
154
155
95
    return calculateConstraintSatisfaction(
156
95
        S, BO.getRHS(), Satisfaction, std::forward<AtomicEvaluator>(Evaluator));
157
975
  } else if (auto *C = dyn_cast<ExprWithCleanups>(ConstraintExpr)) {
158
0
    return calculateConstraintSatisfaction(S, C->getSubExpr(), Satisfaction,
159
0
        std::forward<AtomicEvaluator>(Evaluator));
160
0
  }
161
162
  // An atomic constraint expression
163
975
  ExprResult SubstitutedAtomicExpr = Evaluator(ConstraintExpr);
164
165
975
  if (SubstitutedAtomicExpr.isInvalid())
166
9
    return true;
167
168
966
  if (!SubstitutedAtomicExpr.isUsable())
169
    // Evaluator has decided satisfaction without yielding an expression.
170
16
    return false;
171
172
950
  EnterExpressionEvaluationContext ConstantEvaluated(
173
950
      S, Sema::ExpressionEvaluationContext::ConstantEvaluated);
174
950
  SmallVector<PartialDiagnosticAt, 2> EvaluationDiags;
175
950
  Expr::EvalResult EvalResult;
176
950
  EvalResult.Diag = &EvaluationDiags;
177
950
  if (!SubstitutedAtomicExpr.get()->EvaluateAsConstantExpr(EvalResult,
178
950
                                                           S.Context) ||
179
950
      
!EvaluationDiags.empty()943
) {
180
    // C++2a [temp.constr.atomic]p1
181
    //   ...E shall be a constant expression of type bool.
182
8
    S.Diag(SubstitutedAtomicExpr.get()->getBeginLoc(),
183
8
           diag::err_non_constant_constraint_expression)
184
8
        << SubstitutedAtomicExpr.get()->getSourceRange();
185
8
    for (const PartialDiagnosticAt &PDiag : EvaluationDiags)
186
9
      S.Diag(PDiag.first, PDiag.second);
187
8
    return true;
188
8
  }
189
190
942
  assert(EvalResult.Val.isInt() &&
191
942
         "evaluating bool expression didn't produce int");
192
0
  Satisfaction.IsSatisfied = EvalResult.Val.getInt().getBoolValue();
193
942
  if (!Satisfaction.IsSatisfied)
194
347
    Satisfaction.Details.emplace_back(ConstraintExpr,
195
347
                                      SubstitutedAtomicExpr.get());
196
197
942
  return false;
198
950
}
SemaConcept.cpp:bool calculateConstraintSatisfaction<calculateConstraintSatisfaction(clang::Sema&, clang::NamedDecl const*, llvm::ArrayRef<clang::TemplateArgument>, clang::SourceLocation, clang::MultiLevelTemplateArgumentList&, clang::Expr const*, clang::ConstraintSatisfaction&)::$_5>(clang::Sema&, clang::Expr const*, clang::ConstraintSatisfaction&, calculateConstraintSatisfaction(clang::Sema&, clang::NamedDecl const*, llvm::ArrayRef<clang::TemplateArgument>, clang::SourceLocation, clang::MultiLevelTemplateArgumentList&, clang::Expr const*, clang::ConstraintSatisfaction&)::$_5&&)
Line
Count
Source
127
960
                                AtomicEvaluator &&Evaluator) {
128
960
  ConstraintExpr = ConstraintExpr->IgnoreParenImpCasts();
129
130
960
  if (LogicalBinOp BO = ConstraintExpr) {
131
123
    if (calculateConstraintSatisfaction(S, BO.getLHS(), Satisfaction,
132
123
                                        Evaluator))
133
2
      return true;
134
135
121
    bool IsLHSSatisfied = Satisfaction.IsSatisfied;
136
137
121
    if (BO.isOr() && 
IsLHSSatisfied32
)
138
      // [temp.constr.op] p3
139
      //    A disjunction is a constraint taking two operands. To determine if
140
      //    a disjunction is satisfied, the satisfaction of the first operand
141
      //    is checked. If that is satisfied, the disjunction is satisfied.
142
      //    Otherwise, the disjunction is satisfied if and only if the second
143
      //    operand is satisfied.
144
15
      return false;
145
146
106
    if (BO.isAnd() && 
!IsLHSSatisfied89
)
147
      // [temp.constr.op] p2
148
      //    A conjunction is a constraint taking two operands. To determine if
149
      //    a conjunction is satisfied, the satisfaction of the first operand
150
      //    is checked. If that is not satisfied, the conjunction is not
151
      //    satisfied. Otherwise, the conjunction is satisfied if and only if
152
      //    the second operand is satisfied.
153
19
      return false;
154
155
87
    return calculateConstraintSatisfaction(
156
87
        S, BO.getRHS(), Satisfaction, std::forward<AtomicEvaluator>(Evaluator));
157
837
  } else if (auto *C = dyn_cast<ExprWithCleanups>(ConstraintExpr)) {
158
0
    return calculateConstraintSatisfaction(S, C->getSubExpr(), Satisfaction,
159
0
        std::forward<AtomicEvaluator>(Evaluator));
160
0
  }
161
162
  // An atomic constraint expression
163
837
  ExprResult SubstitutedAtomicExpr = Evaluator(ConstraintExpr);
164
165
837
  if (SubstitutedAtomicExpr.isInvalid())
166
9
    return true;
167
168
828
  if (!SubstitutedAtomicExpr.isUsable())
169
    // Evaluator has decided satisfaction without yielding an expression.
170
10
    return false;
171
172
818
  EnterExpressionEvaluationContext ConstantEvaluated(
173
818
      S, Sema::ExpressionEvaluationContext::ConstantEvaluated);
174
818
  SmallVector<PartialDiagnosticAt, 2> EvaluationDiags;
175
818
  Expr::EvalResult EvalResult;
176
818
  EvalResult.Diag = &EvaluationDiags;
177
818
  if (!SubstitutedAtomicExpr.get()->EvaluateAsConstantExpr(EvalResult,
178
818
                                                           S.Context) ||
179
818
      
!EvaluationDiags.empty()813
) {
180
    // C++2a [temp.constr.atomic]p1
181
    //   ...E shall be a constant expression of type bool.
182
6
    S.Diag(SubstitutedAtomicExpr.get()->getBeginLoc(),
183
6
           diag::err_non_constant_constraint_expression)
184
6
        << SubstitutedAtomicExpr.get()->getSourceRange();
185
6
    for (const PartialDiagnosticAt &PDiag : EvaluationDiags)
186
7
      S.Diag(PDiag.first, PDiag.second);
187
6
    return true;
188
6
  }
189
190
812
  assert(EvalResult.Val.isInt() &&
191
812
         "evaluating bool expression didn't produce int");
192
0
  Satisfaction.IsSatisfied = EvalResult.Val.getInt().getBoolValue();
193
812
  if (!Satisfaction.IsSatisfied)
194
310
    Satisfaction.Details.emplace_back(ConstraintExpr,
195
310
                                      SubstitutedAtomicExpr.get());
196
197
812
  return false;
198
818
}
SemaConcept.cpp:bool calculateConstraintSatisfaction<calculateConstraintSatisfaction(clang::Sema&, clang::NamedDecl const*, llvm::ArrayRef<clang::TemplateArgument>, clang::SourceLocation, clang::MultiLevelTemplateArgumentList&, clang::Expr const*, clang::ConstraintSatisfaction&)::$_5&>(clang::Sema&, clang::Expr const*, clang::ConstraintSatisfaction&, calculateConstraintSatisfaction(clang::Sema&, clang::NamedDecl const*, llvm::ArrayRef<clang::TemplateArgument>, clang::SourceLocation, clang::MultiLevelTemplateArgumentList&, clang::Expr const*, clang::ConstraintSatisfaction&)::$_5&)
Line
Count
Source
127
150
                                AtomicEvaluator &&Evaluator) {
128
150
  ConstraintExpr = ConstraintExpr->IgnoreParenImpCasts();
129
130
150
  if (LogicalBinOp BO = ConstraintExpr) {
131
19
    if (calculateConstraintSatisfaction(S, BO.getLHS(), Satisfaction,
132
19
                                        Evaluator))
133
0
      return true;
134
135
19
    bool IsLHSSatisfied = Satisfaction.IsSatisfied;
136
137
19
    if (BO.isOr() && 
IsLHSSatisfied0
)
138
      // [temp.constr.op] p3
139
      //    A disjunction is a constraint taking two operands. To determine if
140
      //    a disjunction is satisfied, the satisfaction of the first operand
141
      //    is checked. If that is satisfied, the disjunction is satisfied.
142
      //    Otherwise, the disjunction is satisfied if and only if the second
143
      //    operand is satisfied.
144
0
      return false;
145
146
19
    if (BO.isAnd() && !IsLHSSatisfied)
147
      // [temp.constr.op] p2
148
      //    A conjunction is a constraint taking two operands. To determine if
149
      //    a conjunction is satisfied, the satisfaction of the first operand
150
      //    is checked. If that is not satisfied, the conjunction is not
151
      //    satisfied. Otherwise, the conjunction is satisfied if and only if
152
      //    the second operand is satisfied.
153
11
      return false;
154
155
8
    return calculateConstraintSatisfaction(
156
8
        S, BO.getRHS(), Satisfaction, std::forward<AtomicEvaluator>(Evaluator));
157
131
  } else if (auto *C = dyn_cast<ExprWithCleanups>(ConstraintExpr)) {
158
0
    return calculateConstraintSatisfaction(S, C->getSubExpr(), Satisfaction,
159
0
        std::forward<AtomicEvaluator>(Evaluator));
160
0
  }
161
162
  // An atomic constraint expression
163
131
  ExprResult SubstitutedAtomicExpr = Evaluator(ConstraintExpr);
164
165
131
  if (SubstitutedAtomicExpr.isInvalid())
166
0
    return true;
167
168
131
  if (!SubstitutedAtomicExpr.isUsable())
169
    // Evaluator has decided satisfaction without yielding an expression.
170
6
    return false;
171
172
125
  EnterExpressionEvaluationContext ConstantEvaluated(
173
125
      S, Sema::ExpressionEvaluationContext::ConstantEvaluated);
174
125
  SmallVector<PartialDiagnosticAt, 2> EvaluationDiags;
175
125
  Expr::EvalResult EvalResult;
176
125
  EvalResult.Diag = &EvaluationDiags;
177
125
  if (!SubstitutedAtomicExpr.get()->EvaluateAsConstantExpr(EvalResult,
178
125
                                                           S.Context) ||
179
125
      
!EvaluationDiags.empty()123
) {
180
    // C++2a [temp.constr.atomic]p1
181
    //   ...E shall be a constant expression of type bool.
182
2
    S.Diag(SubstitutedAtomicExpr.get()->getBeginLoc(),
183
2
           diag::err_non_constant_constraint_expression)
184
2
        << SubstitutedAtomicExpr.get()->getSourceRange();
185
2
    for (const PartialDiagnosticAt &PDiag : EvaluationDiags)
186
2
      S.Diag(PDiag.first, PDiag.second);
187
2
    return true;
188
2
  }
189
190
123
  assert(EvalResult.Val.isInt() &&
191
123
         "evaluating bool expression didn't produce int");
192
0
  Satisfaction.IsSatisfied = EvalResult.Val.getInt().getBoolValue();
193
123
  if (!Satisfaction.IsSatisfied)
194
30
    Satisfaction.Details.emplace_back(ConstraintExpr,
195
30
                                      SubstitutedAtomicExpr.get());
196
197
123
  return false;
198
125
}
SemaConcept.cpp:bool calculateConstraintSatisfaction<clang::Sema::CheckConstraintSatisfaction(clang::Expr const*, clang::ConstraintSatisfaction&)::$_1>(clang::Sema&, clang::Expr const*, clang::ConstraintSatisfaction&, clang::Sema::CheckConstraintSatisfaction(clang::Expr const*, clang::ConstraintSatisfaction&)::$_1&&)
Line
Count
Source
127
7
                                AtomicEvaluator &&Evaluator) {
128
7
  ConstraintExpr = ConstraintExpr->IgnoreParenImpCasts();
129
130
7
  if (LogicalBinOp BO = ConstraintExpr) {
131
0
    if (calculateConstraintSatisfaction(S, BO.getLHS(), Satisfaction,
132
0
                                        Evaluator))
133
0
      return true;
134
135
0
    bool IsLHSSatisfied = Satisfaction.IsSatisfied;
136
137
0
    if (BO.isOr() && IsLHSSatisfied)
138
      // [temp.constr.op] p3
139
      //    A disjunction is a constraint taking two operands. To determine if
140
      //    a disjunction is satisfied, the satisfaction of the first operand
141
      //    is checked. If that is satisfied, the disjunction is satisfied.
142
      //    Otherwise, the disjunction is satisfied if and only if the second
143
      //    operand is satisfied.
144
0
      return false;
145
146
0
    if (BO.isAnd() && !IsLHSSatisfied)
147
      // [temp.constr.op] p2
148
      //    A conjunction is a constraint taking two operands. To determine if
149
      //    a conjunction is satisfied, the satisfaction of the first operand
150
      //    is checked. If that is not satisfied, the conjunction is not
151
      //    satisfied. Otherwise, the conjunction is satisfied if and only if
152
      //    the second operand is satisfied.
153
0
      return false;
154
155
0
    return calculateConstraintSatisfaction(
156
0
        S, BO.getRHS(), Satisfaction, std::forward<AtomicEvaluator>(Evaluator));
157
7
  } else if (auto *C = dyn_cast<ExprWithCleanups>(ConstraintExpr)) {
158
0
    return calculateConstraintSatisfaction(S, C->getSubExpr(), Satisfaction,
159
0
        std::forward<AtomicEvaluator>(Evaluator));
160
0
  }
161
162
  // An atomic constraint expression
163
7
  ExprResult SubstitutedAtomicExpr = Evaluator(ConstraintExpr);
164
165
7
  if (SubstitutedAtomicExpr.isInvalid())
166
0
    return true;
167
168
7
  if (!SubstitutedAtomicExpr.isUsable())
169
    // Evaluator has decided satisfaction without yielding an expression.
170
0
    return false;
171
172
7
  EnterExpressionEvaluationContext ConstantEvaluated(
173
7
      S, Sema::ExpressionEvaluationContext::ConstantEvaluated);
174
7
  SmallVector<PartialDiagnosticAt, 2> EvaluationDiags;
175
7
  Expr::EvalResult EvalResult;
176
7
  EvalResult.Diag = &EvaluationDiags;
177
7
  if (!SubstitutedAtomicExpr.get()->EvaluateAsConstantExpr(EvalResult,
178
7
                                                           S.Context) ||
179
7
      !EvaluationDiags.empty()) {
180
    // C++2a [temp.constr.atomic]p1
181
    //   ...E shall be a constant expression of type bool.
182
0
    S.Diag(SubstitutedAtomicExpr.get()->getBeginLoc(),
183
0
           diag::err_non_constant_constraint_expression)
184
0
        << SubstitutedAtomicExpr.get()->getSourceRange();
185
0
    for (const PartialDiagnosticAt &PDiag : EvaluationDiags)
186
0
      S.Diag(PDiag.first, PDiag.second);
187
0
    return true;
188
0
  }
189
190
7
  assert(EvalResult.Val.isInt() &&
191
7
         "evaluating bool expression didn't produce int");
192
0
  Satisfaction.IsSatisfied = EvalResult.Val.getInt().getBoolValue();
193
7
  if (!Satisfaction.IsSatisfied)
194
7
    Satisfaction.Details.emplace_back(ConstraintExpr,
195
7
                                      SubstitutedAtomicExpr.get());
196
197
7
  return false;
198
7
}
Unexecuted instantiation: SemaConcept.cpp:bool calculateConstraintSatisfaction<clang::Sema::CheckConstraintSatisfaction(clang::Expr const*, clang::ConstraintSatisfaction&)::$_1&>(clang::Sema&, clang::Expr const*, clang::ConstraintSatisfaction&, clang::Sema::CheckConstraintSatisfaction(clang::Expr const*, clang::ConstraintSatisfaction&)::$_1&)
199
200
static bool calculateConstraintSatisfaction(
201
    Sema &S, const NamedDecl *Template, ArrayRef<TemplateArgument> TemplateArgs,
202
    SourceLocation TemplateNameLoc, MultiLevelTemplateArgumentList &MLTAL,
203
873
    const Expr *ConstraintExpr, ConstraintSatisfaction &Satisfaction) {
204
873
  return calculateConstraintSatisfaction(
205
968
      S, ConstraintExpr, Satisfaction, [&](const Expr *AtomicExpr) {
206
968
        EnterExpressionEvaluationContext ConstantEvaluated(
207
968
            S, Sema::ExpressionEvaluationContext::ConstantEvaluated);
208
209
        // Atomic constraint - substitute arguments and check satisfaction.
210
968
        ExprResult SubstitutedExpression;
211
968
        {
212
968
          TemplateDeductionInfo Info(TemplateNameLoc);
213
968
          Sema::InstantiatingTemplate Inst(S, AtomicExpr->getBeginLoc(),
214
968
              Sema::InstantiatingTemplate::ConstraintSubstitution{},
215
968
              const_cast<NamedDecl *>(Template), Info,
216
968
              AtomicExpr->getSourceRange());
217
968
          if (Inst.isInvalid())
218
0
            return ExprError();
219
          // We do not want error diagnostics escaping here.
220
968
          Sema::SFINAETrap Trap(S);
221
968
          SubstitutedExpression = S.SubstExpr(const_cast<Expr *>(AtomicExpr),
222
968
                                              MLTAL);
223
          // Substitution might have stripped off a contextual conversion to
224
          // bool if this is the operand of an '&&' or '||'. For example, we
225
          // might lose an lvalue-to-rvalue conversion here. If so, put it back
226
          // before we try to evaluate.
227
968
          if (!SubstitutedExpression.isInvalid())
228
948
            SubstitutedExpression =
229
948
                S.PerformContextuallyConvertToBool(SubstitutedExpression.get());
230
968
          if (SubstitutedExpression.isInvalid() || 
Trap.hasErrorOccurred()948
) {
231
            // C++2a [temp.constr.atomic]p1
232
            //   ...If substitution results in an invalid type or expression, the
233
            //   constraint is not satisfied.
234
21
            if (!Trap.hasErrorOccurred())
235
              // A non-SFINAE error has occured as a result of this
236
              // substitution.
237
5
              return ExprError();
238
239
16
            PartialDiagnosticAt SubstDiag{SourceLocation(),
240
16
                                          PartialDiagnostic::NullDiagnostic()};
241
16
            Info.takeSFINAEDiagnostic(SubstDiag);
242
            // FIXME: Concepts: This is an unfortunate consequence of there
243
            //  being no serialization code for PartialDiagnostics and the fact
244
            //  that serializing them would likely take a lot more storage than
245
            //  just storing them as strings. We would still like, in the
246
            //  future, to serialize the proper PartialDiagnostic as serializing
247
            //  it as a string defeats the purpose of the diagnostic mechanism.
248
16
            SmallString<128> DiagString;
249
16
            DiagString = ": ";
250
16
            SubstDiag.second.EmitToString(S.getDiagnostics(), DiagString);
251
16
            unsigned MessageSize = DiagString.size();
252
16
            char *Mem = new (S.Context) char[MessageSize];
253
16
            memcpy(Mem, DiagString.c_str(), MessageSize);
254
16
            Satisfaction.Details.emplace_back(
255
16
                AtomicExpr,
256
16
                new (S.Context) ConstraintSatisfaction::SubstitutionDiagnostic{
257
16
                        SubstDiag.first, StringRef(Mem, MessageSize)});
258
16
            Satisfaction.IsSatisfied = false;
259
16
            return ExprEmpty();
260
21
          }
261
968
        }
262
263
947
        if (!S.CheckConstraintExpression(SubstitutedExpression.get()))
264
4
          return ExprError();
265
266
943
        return SubstitutedExpression;
267
947
      });
268
873
}
269
270
static bool CheckConstraintSatisfaction(Sema &S, const NamedDecl *Template,
271
                                        ArrayRef<const Expr *> ConstraintExprs,
272
                                        ArrayRef<TemplateArgument> TemplateArgs,
273
                                        SourceRange TemplateIDRange,
274
892
                                        ConstraintSatisfaction &Satisfaction) {
275
892
  if (ConstraintExprs.empty()) {
276
0
    Satisfaction.IsSatisfied = true;
277
0
    return false;
278
0
  }
279
280
892
  for (auto& Arg : TemplateArgs)
281
887
    if (Arg.isInstantiationDependent()) {
282
      // No need to check satisfaction for dependent constraint expressions.
283
45
      Satisfaction.IsSatisfied = true;
284
45
      return false;
285
45
    }
286
287
847
  Sema::InstantiatingTemplate Inst(S, TemplateIDRange.getBegin(),
288
847
      Sema::InstantiatingTemplate::ConstraintsCheck{},
289
847
      const_cast<NamedDecl *>(Template), TemplateArgs, TemplateIDRange);
290
847
  if (Inst.isInvalid())
291
0
    return true;
292
293
847
  MultiLevelTemplateArgumentList MLTAL;
294
847
  MLTAL.addOuterTemplateArguments(TemplateArgs);
295
296
873
  for (const Expr *ConstraintExpr : ConstraintExprs) {
297
873
    if (calculateConstraintSatisfaction(S, Template, TemplateArgs,
298
873
                                        TemplateIDRange.getBegin(), MLTAL,
299
873
                                        ConstraintExpr, Satisfaction))
300
17
      return true;
301
856
    if (!Satisfaction.IsSatisfied)
302
      // [temp.constr.op] p2
303
      //   [...] To determine if a conjunction is satisfied, the satisfaction
304
      //   of the first operand is checked. If that is not satisfied, the
305
      //   conjunction is not satisfied. [...]
306
339
      return false;
307
856
  }
308
491
  return false;
309
847
}
310
311
bool Sema::CheckConstraintSatisfaction(
312
    const NamedDecl *Template, ArrayRef<const Expr *> ConstraintExprs,
313
    ArrayRef<TemplateArgument> TemplateArgs, SourceRange TemplateIDRange,
314
6.95M
    ConstraintSatisfaction &OutSatisfaction) {
315
6.95M
  if (ConstraintExprs.empty()) {
316
6.95M
    OutSatisfaction.IsSatisfied = true;
317
6.95M
    return false;
318
6.95M
  }
319
320
1.41k
  llvm::FoldingSetNodeID ID;
321
1.41k
  void *InsertPos;
322
1.41k
  ConstraintSatisfaction *Satisfaction = nullptr;
323
1.41k
  bool ShouldCache = LangOpts.ConceptSatisfactionCaching && 
Template1.40k
;
324
1.41k
  if (ShouldCache) {
325
1.34k
    ConstraintSatisfaction::Profile(ID, Context, Template, TemplateArgs);
326
1.34k
    Satisfaction = SatisfactionCache.FindNodeOrInsertPos(ID, InsertPos);
327
1.34k
    if (Satisfaction) {
328
519
      OutSatisfaction = *Satisfaction;
329
519
      return false;
330
519
    }
331
821
    Satisfaction = new ConstraintSatisfaction(Template, TemplateArgs);
332
821
  } else {
333
71
    Satisfaction = &OutSatisfaction;
334
71
  }
335
892
  if (::CheckConstraintSatisfaction(*this, Template, ConstraintExprs,
336
892
                                    TemplateArgs, TemplateIDRange,
337
892
                                    *Satisfaction)) {
338
17
    if (ShouldCache)
339
16
      delete Satisfaction;
340
17
    return true;
341
17
  }
342
343
875
  if (ShouldCache) {
344
    // We cannot use InsertNode here because CheckConstraintSatisfaction might
345
    // have invalidated it.
346
805
    SatisfactionCache.InsertNode(Satisfaction);
347
805
    OutSatisfaction = *Satisfaction;
348
805
  }
349
875
  return false;
350
892
}
351
352
bool Sema::CheckConstraintSatisfaction(const Expr *ConstraintExpr,
353
7
                                       ConstraintSatisfaction &Satisfaction) {
354
7
  return calculateConstraintSatisfaction(
355
7
      *this, ConstraintExpr, Satisfaction,
356
7
      [](const Expr *AtomicExpr) -> ExprResult {
357
7
        return ExprResult(const_cast<Expr *>(AtomicExpr));
358
7
      });
359
7
}
360
361
bool Sema::CheckFunctionConstraints(const FunctionDecl *FD,
362
                                    ConstraintSatisfaction &Satisfaction,
363
174
                                    SourceLocation UsageLoc) {
364
174
  const Expr *RC = FD->getTrailingRequiresClause();
365
174
  if (RC->isInstantiationDependent()) {
366
0
    Satisfaction.IsSatisfied = true;
367
0
    return false;
368
0
  }
369
174
  Qualifiers ThisQuals;
370
174
  CXXRecordDecl *Record = nullptr;
371
174
  if (auto *Method = dyn_cast<CXXMethodDecl>(FD)) {
372
77
    ThisQuals = Method->getMethodQualifiers();
373
77
    Record = const_cast<CXXRecordDecl *>(Method->getParent());
374
77
  }
375
174
  CXXThisScopeRAII ThisScope(*this, Record, ThisQuals, Record != nullptr);
376
  // We substitute with empty arguments in order to rebuild the atomic
377
  // constraint in a constant-evaluated context.
378
  // FIXME: Should this be a dedicated TreeTransform?
379
174
  return CheckConstraintSatisfaction(
380
174
      FD, {RC}, /*TemplateArgs=*/{},
381
174
      SourceRange(UsageLoc.isValid() ? 
UsageLoc68
:
FD->getLocation()106
),
382
174
      Satisfaction);
383
174
}
384
385
bool Sema::EnsureTemplateArgumentListConstraints(
386
    TemplateDecl *TD, ArrayRef<TemplateArgument> TemplateArgs,
387
6.61M
    SourceRange TemplateIDRange) {
388
6.61M
  ConstraintSatisfaction Satisfaction;
389
6.61M
  llvm::SmallVector<const Expr *, 3> AssociatedConstraints;
390
6.61M
  TD->getAssociatedConstraints(AssociatedConstraints);
391
6.61M
  if (CheckConstraintSatisfaction(TD, AssociatedConstraints, TemplateArgs,
392
6.61M
                                  TemplateIDRange, Satisfaction))
393
3
    return true;
394
395
6.61M
  if (!Satisfaction.IsSatisfied) {
396
108
    SmallString<128> TemplateArgString;
397
108
    TemplateArgString = " ";
398
108
    TemplateArgString += getTemplateArgumentBindingsText(
399
108
        TD->getTemplateParameters(), TemplateArgs.data(), TemplateArgs.size());
400
401
108
    Diag(TemplateIDRange.getBegin(),
402
108
         diag::err_template_arg_list_constraints_not_satisfied)
403
108
        << (int)getTemplateNameKindForDiagnostics(TemplateName(TD)) << TD
404
108
        << TemplateArgString << TemplateIDRange;
405
108
    DiagnoseUnsatisfiedConstraint(Satisfaction);
406
108
    return true;
407
108
  }
408
6.61M
  return false;
409
6.61M
}
410
411
static void diagnoseUnsatisfiedRequirement(Sema &S,
412
                                           concepts::ExprRequirement *Req,
413
29
                                           bool First) {
414
29
  assert(!Req->isSatisfied()
415
29
         && "Diagnose() can only be used on an unsatisfied requirement");
416
0
  switch (Req->getSatisfactionStatus()) {
417
0
    case concepts::ExprRequirement::SS_Dependent:
418
0
      llvm_unreachable("Diagnosing a dependent requirement");
419
0
      break;
420
24
    case concepts::ExprRequirement::SS_ExprSubstitutionFailure: {
421
24
      auto *SubstDiag = Req->getExprSubstitutionDiagnostic();
422
24
      if (!SubstDiag->DiagMessage.empty())
423
24
        S.Diag(SubstDiag->DiagLoc,
424
24
               diag::note_expr_requirement_expr_substitution_error)
425
24
               << (int)First << SubstDiag->SubstitutedEntity
426
24
               << SubstDiag->DiagMessage;
427
0
      else
428
0
        S.Diag(SubstDiag->DiagLoc,
429
0
               diag::note_expr_requirement_expr_unknown_substitution_error)
430
0
            << (int)First << SubstDiag->SubstitutedEntity;
431
24
      break;
432
0
    }
433
2
    case concepts::ExprRequirement::SS_NoexceptNotMet:
434
2
      S.Diag(Req->getNoexceptLoc(),
435
2
             diag::note_expr_requirement_noexcept_not_met)
436
2
          << (int)First << Req->getExpr();
437
2
      break;
438
1
    case concepts::ExprRequirement::SS_TypeRequirementSubstitutionFailure: {
439
1
      auto *SubstDiag =
440
1
          Req->getReturnTypeRequirement().getSubstitutionDiagnostic();
441
1
      if (!SubstDiag->DiagMessage.empty())
442
1
        S.Diag(SubstDiag->DiagLoc,
443
1
               diag::note_expr_requirement_type_requirement_substitution_error)
444
1
            << (int)First << SubstDiag->SubstitutedEntity
445
1
            << SubstDiag->DiagMessage;
446
0
      else
447
0
        S.Diag(SubstDiag->DiagLoc,
448
0
               diag::note_expr_requirement_type_requirement_unknown_substitution_error)
449
0
            << (int)First << SubstDiag->SubstitutedEntity;
450
1
      break;
451
0
    }
452
2
    case concepts::ExprRequirement::SS_ConstraintsNotSatisfied: {
453
2
      ConceptSpecializationExpr *ConstraintExpr =
454
2
          Req->getReturnTypeRequirementSubstitutedConstraintExpr();
455
2
      if (ConstraintExpr->getTemplateArgsAsWritten()->NumTemplateArgs == 1) {
456
        // A simple case - expr type is the type being constrained and the concept
457
        // was not provided arguments.
458
1
        Expr *e = Req->getExpr();
459
1
        S.Diag(e->getBeginLoc(),
460
1
               diag::note_expr_requirement_constraints_not_satisfied_simple)
461
1
            << (int)First << S.getDecltypeForParenthesizedExpr(e)
462
1
            << ConstraintExpr->getNamedConcept();
463
1
      } else {
464
1
        S.Diag(ConstraintExpr->getBeginLoc(),
465
1
               diag::note_expr_requirement_constraints_not_satisfied)
466
1
            << (int)First << ConstraintExpr;
467
1
      }
468
2
      S.DiagnoseUnsatisfiedConstraint(ConstraintExpr->getSatisfaction());
469
2
      break;
470
0
    }
471
0
    case concepts::ExprRequirement::SS_Satisfied:
472
0
      llvm_unreachable("We checked this above");
473
29
  }
474
29
}
475
476
static void diagnoseUnsatisfiedRequirement(Sema &S,
477
                                           concepts::TypeRequirement *Req,
478
16
                                           bool First) {
479
16
  assert(!Req->isSatisfied()
480
16
         && "Diagnose() can only be used on an unsatisfied requirement");
481
0
  switch (Req->getSatisfactionStatus()) {
482
0
  case concepts::TypeRequirement::SS_Dependent:
483
0
    llvm_unreachable("Diagnosing a dependent requirement");
484
0
    return;
485
16
  case concepts::TypeRequirement::SS_SubstitutionFailure: {
486
16
    auto *SubstDiag = Req->getSubstitutionDiagnostic();
487
16
    if (!SubstDiag->DiagMessage.empty())
488
15
      S.Diag(SubstDiag->DiagLoc,
489
15
             diag::note_type_requirement_substitution_error) << (int)First
490
15
          << SubstDiag->SubstitutedEntity << SubstDiag->DiagMessage;
491
1
    else
492
1
      S.Diag(SubstDiag->DiagLoc,
493
1
             diag::note_type_requirement_unknown_substitution_error)
494
1
          << (int)First << SubstDiag->SubstitutedEntity;
495
16
    return;
496
0
  }
497
0
  default:
498
0
    llvm_unreachable("Unknown satisfaction status");
499
0
    return;
500
16
  }
501
16
}
502
503
static void diagnoseUnsatisfiedRequirement(Sema &S,
504
                                           concepts::NestedRequirement *Req,
505
12
                                           bool First) {
506
12
  if (Req->isSubstitutionFailure()) {
507
2
    concepts::Requirement::SubstitutionDiagnostic *SubstDiag =
508
2
        Req->getSubstitutionDiagnostic();
509
2
    if (!SubstDiag->DiagMessage.empty())
510
2
      S.Diag(SubstDiag->DiagLoc,
511
2
             diag::note_nested_requirement_substitution_error)
512
2
             << (int)First << SubstDiag->SubstitutedEntity
513
2
             << SubstDiag->DiagMessage;
514
0
    else
515
0
      S.Diag(SubstDiag->DiagLoc,
516
0
             diag::note_nested_requirement_unknown_substitution_error)
517
0
          << (int)First << SubstDiag->SubstitutedEntity;
518
2
    return;
519
2
  }
520
10
  S.DiagnoseUnsatisfiedConstraint(Req->getConstraintSatisfaction(), First);
521
10
}
522
523
524
static void diagnoseWellFormedUnsatisfiedConstraintExpr(Sema &S,
525
                                                        Expr *SubstExpr,
526
358
                                                        bool First = true) {
527
358
  SubstExpr = SubstExpr->IgnoreParenImpCasts();
528
358
  if (BinaryOperator *BO = dyn_cast<BinaryOperator>(SubstExpr)) {
529
116
    switch (BO->getOpcode()) {
530
    // These two cases will in practice only be reached when using fold
531
    // expressions with || and &&, since otherwise the || and && will have been
532
    // broken down into atomic constraints during satisfaction checking.
533
11
    case BO_LOr:
534
      // Or evaluated to false - meaning both RHS and LHS evaluated to false.
535
11
      diagnoseWellFormedUnsatisfiedConstraintExpr(S, BO->getLHS(), First);
536
11
      diagnoseWellFormedUnsatisfiedConstraintExpr(S, BO->getRHS(),
537
11
                                                  /*First=*/false);
538
11
      return;
539
30
    case BO_LAnd: {
540
30
      bool LHSSatisfied =
541
30
          BO->getLHS()->EvaluateKnownConstInt(S.Context).getBoolValue();
542
30
      if (LHSSatisfied) {
543
        // LHS is true, so RHS must be false.
544
12
        diagnoseWellFormedUnsatisfiedConstraintExpr(S, BO->getRHS(), First);
545
12
        return;
546
12
      }
547
      // LHS is false
548
18
      diagnoseWellFormedUnsatisfiedConstraintExpr(S, BO->getLHS(), First);
549
550
      // RHS might also be false
551
18
      bool RHSSatisfied =
552
18
          BO->getRHS()->EvaluateKnownConstInt(S.Context).getBoolValue();
553
18
      if (!RHSSatisfied)
554
13
        diagnoseWellFormedUnsatisfiedConstraintExpr(S, BO->getRHS(),
555
13
                                                    /*First=*/false);
556
18
      return;
557
30
    }
558
7
    case BO_GE:
559
9
    case BO_LE:
560
17
    case BO_GT:
561
18
    case BO_LT:
562
66
    case BO_EQ:
563
68
    case BO_NE:
564
68
      if (BO->getLHS()->getType()->isIntegerType() &&
565
68
          BO->getRHS()->getType()->isIntegerType()) {
566
68
        Expr::EvalResult SimplifiedLHS;
567
68
        Expr::EvalResult SimplifiedRHS;
568
68
        BO->getLHS()->EvaluateAsInt(SimplifiedLHS, S.Context,
569
68
                                    Expr::SE_NoSideEffects,
570
68
                                    /*InConstantContext=*/true);
571
68
        BO->getRHS()->EvaluateAsInt(SimplifiedRHS, S.Context,
572
68
                                    Expr::SE_NoSideEffects,
573
68
                                    /*InConstantContext=*/true);
574
68
        if (!SimplifiedLHS.Diag && ! SimplifiedRHS.Diag) {
575
68
          S.Diag(SubstExpr->getBeginLoc(),
576
68
                 diag::note_atomic_constraint_evaluated_to_false_elaborated)
577
68
              << (int)First << SubstExpr
578
68
              << toString(SimplifiedLHS.Val.getInt(), 10)
579
68
              << BinaryOperator::getOpcodeStr(BO->getOpcode())
580
68
              << toString(SimplifiedRHS.Val.getInt(), 10);
581
68
          return;
582
68
        }
583
68
      }
584
0
      break;
585
586
7
    default:
587
7
      break;
588
116
    }
589
242
  } else if (auto *CSE = dyn_cast<ConceptSpecializationExpr>(SubstExpr)) {
590
87
    if (CSE->getTemplateArgsAsWritten()->NumTemplateArgs == 1) {
591
52
      S.Diag(
592
52
          CSE->getSourceRange().getBegin(),
593
52
          diag::
594
52
          note_single_arg_concept_specialization_constraint_evaluated_to_false)
595
52
          << (int)First
596
52
          << CSE->getTemplateArgsAsWritten()->arguments()[0].getArgument()
597
52
          << CSE->getNamedConcept();
598
52
    } else {
599
35
      S.Diag(SubstExpr->getSourceRange().getBegin(),
600
35
             diag::note_concept_specialization_constraint_evaluated_to_false)
601
35
          << (int)First << CSE;
602
35
    }
603
87
    S.DiagnoseUnsatisfiedConstraint(CSE->getSatisfaction());
604
87
    return;
605
155
  } else if (auto *RE = dyn_cast<RequiresExpr>(SubstExpr)) {
606
57
    for (concepts::Requirement *Req : RE->getRequirements())
607
60
      if (!Req->isDependent() && !Req->isSatisfied()) {
608
57
        if (auto *E = dyn_cast<concepts::ExprRequirement>(Req))
609
29
          diagnoseUnsatisfiedRequirement(S, E, First);
610
28
        else if (auto *T = dyn_cast<concepts::TypeRequirement>(Req))
611
16
          diagnoseUnsatisfiedRequirement(S, T, First);
612
12
        else
613
12
          diagnoseUnsatisfiedRequirement(
614
12
              S, cast<concepts::NestedRequirement>(Req), First);
615
57
        break;
616
57
      }
617
57
    return;
618
57
  }
619
620
105
  S.Diag(SubstExpr->getSourceRange().getBegin(),
621
105
         diag::note_atomic_constraint_evaluated_to_false)
622
105
      << (int)First << SubstExpr;
623
105
}
624
625
template<typename SubstitutionDiagnostic>
626
static void diagnoseUnsatisfiedConstraintExpr(
627
    Sema &S, const Expr *E,
628
    const llvm::PointerUnion<Expr *, SubstitutionDiagnostic *> &Record,
629
298
    bool First = true) {
630
298
  if (auto *Diag = Record.template dyn_cast<SubstitutionDiagnostic *>()){
631
5
    S.Diag(Diag->first, diag::note_substituted_constraint_expr_is_ill_formed)
632
5
        << Diag->second;
633
5
    return;
634
5
  }
635
636
293
  diagnoseWellFormedUnsatisfiedConstraintExpr(S,
637
293
      Record.template get<Expr *>(), First);
638
293
}
639
640
void
641
Sema::DiagnoseUnsatisfiedConstraint(const ConstraintSatisfaction& Satisfaction,
642
198
                                    bool First) {
643
198
  assert(!Satisfaction.IsSatisfied &&
644
198
         "Attempted to diagnose a satisfied constraint");
645
199
  for (auto &Pair : Satisfaction.Details) {
646
199
    diagnoseUnsatisfiedConstraintExpr(*this, Pair.first, Pair.second, First);
647
199
    First = false;
648
199
  }
649
198
}
650
651
void Sema::DiagnoseUnsatisfiedConstraint(
652
    const ASTConstraintSatisfaction &Satisfaction,
653
99
    bool First) {
654
99
  assert(!Satisfaction.IsSatisfied &&
655
99
         "Attempted to diagnose a satisfied constraint");
656
99
  for (auto &Pair : Satisfaction) {
657
99
    diagnoseUnsatisfiedConstraintExpr(*this, Pair.first, Pair.second, First);
658
99
    First = false;
659
99
  }
660
99
}
661
662
const NormalizedConstraint *
663
Sema::getNormalizedAssociatedConstraints(
664
313
    NamedDecl *ConstrainedDecl, ArrayRef<const Expr *> AssociatedConstraints) {
665
313
  auto CacheEntry = NormalizationCache.find(ConstrainedDecl);
666
313
  if (CacheEntry == NormalizationCache.end()) {
667
133
    auto Normalized =
668
133
        NormalizedConstraint::fromConstraintExprs(*this, ConstrainedDecl,
669
133
                                                  AssociatedConstraints);
670
133
    CacheEntry =
671
133
        NormalizationCache
672
133
            .try_emplace(ConstrainedDecl,
673
133
                         Normalized
674
133
                             ? new (Context) NormalizedConstraint(
675
131
                                 std::move(*Normalized))
676
133
                             : 
nullptr2
)
677
133
            .first;
678
133
  }
679
313
  return CacheEntry->second;
680
313
}
681
682
static bool substituteParameterMappings(Sema &S, NormalizedConstraint &N,
683
    ConceptDecl *Concept, ArrayRef<TemplateArgument> TemplateArgs,
684
142
    const ASTTemplateArgumentListInfo *ArgsAsWritten) {
685
142
  if (!N.isAtomic()) {
686
16
    if (substituteParameterMappings(S, N.getLHS(), Concept, TemplateArgs,
687
16
                                    ArgsAsWritten))
688
0
      return true;
689
16
    return substituteParameterMappings(S, N.getRHS(), Concept, TemplateArgs,
690
16
                                       ArgsAsWritten);
691
16
  }
692
126
  TemplateParameterList *TemplateParams = Concept->getTemplateParameters();
693
694
126
  AtomicConstraint &Atomic = *N.getAtomicConstraint();
695
126
  TemplateArgumentListInfo SubstArgs;
696
126
  MultiLevelTemplateArgumentList MLTAL;
697
126
  MLTAL.addOuterTemplateArguments(TemplateArgs);
698
126
  if (!Atomic.ParameterMapping) {
699
103
    llvm::SmallBitVector OccurringIndices(TemplateParams->size());
700
103
    S.MarkUsedTemplateParameters(Atomic.ConstraintExpr, /*OnlyDeduced=*/false,
701
103
                                 /*Depth=*/0, OccurringIndices);
702
103
    Atomic.ParameterMapping.emplace(
703
103
        MutableArrayRef<TemplateArgumentLoc>(
704
103
            new (S.Context) TemplateArgumentLoc[OccurringIndices.count()],
705
103
            OccurringIndices.count()));
706
211
    for (unsigned I = 0, J = 0, C = TemplateParams->size(); I != C; 
++I108
)
707
108
      if (OccurringIndices[I])
708
89
        new (&(*Atomic.ParameterMapping)[J++]) TemplateArgumentLoc(
709
89
            S.getIdentityTemplateArgumentLoc(TemplateParams->begin()[I],
710
                // Here we assume we do not support things like
711
                // template<typename A, typename B>
712
                // concept C = ...;
713
                //
714
                // template<typename... Ts> requires C<Ts...>
715
                // struct S { };
716
                // The above currently yields a diagnostic.
717
                // We still might have default arguments for concept parameters.
718
89
                ArgsAsWritten->NumTemplateArgs > I ?
719
89
                ArgsAsWritten->arguments()[I].getLocation() :
720
89
                
SourceLocation()0
));
721
103
  }
722
126
  Sema::InstantiatingTemplate Inst(
723
126
      S, ArgsAsWritten->arguments().front().getSourceRange().getBegin(),
724
126
      Sema::InstantiatingTemplate::ParameterMappingSubstitution{}, Concept,
725
126
      SourceRange(ArgsAsWritten->arguments()[0].getSourceRange().getBegin(),
726
126
                  ArgsAsWritten->arguments().back().getSourceRange().getEnd()));
727
126
  if (S.SubstTemplateArguments(*Atomic.ParameterMapping, MLTAL, SubstArgs))
728
1
    return true;
729
125
  Atomic.ParameterMapping.emplace(
730
125
        MutableArrayRef<TemplateArgumentLoc>(
731
125
            new (S.Context) TemplateArgumentLoc[SubstArgs.size()],
732
125
            SubstArgs.size()));
733
125
  std::copy(SubstArgs.arguments().begin(), SubstArgs.arguments().end(),
734
125
            N.getAtomicConstraint()->ParameterMapping->begin());
735
125
  return false;
736
126
}
737
738
Optional<NormalizedConstraint>
739
NormalizedConstraint::fromConstraintExprs(Sema &S, NamedDecl *D,
740
133
                                          ArrayRef<const Expr *> E) {
741
133
  assert(E.size() != 0);
742
0
  auto First = fromConstraintExpr(S, D, E[0]);
743
133
  if (E.size() == 1)
744
133
    return First;
745
0
  auto Second = fromConstraintExpr(S, D, E[1]);
746
0
  if (!Second)
747
0
    return None;
748
0
  llvm::Optional<NormalizedConstraint> Conjunction;
749
0
  Conjunction.emplace(S.Context, std::move(*First), std::move(*Second),
750
0
                      CCK_Conjunction);
751
0
  for (unsigned I = 2; I < E.size(); ++I) {
752
0
    auto Next = fromConstraintExpr(S, D, E[I]);
753
0
    if (!Next)
754
0
      return llvm::Optional<NormalizedConstraint>{};
755
0
    NormalizedConstraint NewConjunction(S.Context, std::move(*Conjunction),
756
0
                                        std::move(*Next), CCK_Conjunction);
757
0
    *Conjunction = std::move(NewConjunction);
758
0
  }
759
0
  return Conjunction;
760
0
}
761
762
llvm::Optional<NormalizedConstraint>
763
236
NormalizedConstraint::fromConstraintExpr(Sema &S, NamedDecl *D, const Expr *E) {
764
236
  assert(E != nullptr);
765
766
  // C++ [temp.constr.normal]p1.1
767
  // [...]
768
  // - The normal form of an expression (E) is the normal form of E.
769
  // [...]
770
0
  E = E->IgnoreParenImpCasts();
771
236
  if (LogicalBinOp BO = E) {
772
52
    auto LHS = fromConstraintExpr(S, D, BO.getLHS());
773
52
    if (!LHS)
774
1
      return None;
775
51
    auto RHS = fromConstraintExpr(S, D, BO.getRHS());
776
51
    if (!RHS)
777
0
      return None;
778
779
51
    return NormalizedConstraint(S.Context, std::move(*LHS), std::move(*RHS),
780
51
                                BO.isAnd() ? 
CCK_Conjunction46
:
CCK_Disjunction5
);
781
184
  } else if (auto *CSE = dyn_cast<const ConceptSpecializationExpr>(E)) {
782
111
    const NormalizedConstraint *SubNF;
783
111
    {
784
111
      Sema::InstantiatingTemplate Inst(
785
111
          S, CSE->getExprLoc(),
786
111
          Sema::InstantiatingTemplate::ConstraintNormalization{}, D,
787
111
          CSE->getSourceRange());
788
      // C++ [temp.constr.normal]p1.1
789
      // [...]
790
      // The normal form of an id-expression of the form C<A1, A2, ..., AN>,
791
      // where C names a concept, is the normal form of the
792
      // constraint-expression of C, after substituting A1, A2, ..., AN for C’s
793
      // respective template parameters in the parameter mappings in each atomic
794
      // constraint. If any such substitution results in an invalid type or
795
      // expression, the program is ill-formed; no diagnostic is required.
796
      // [...]
797
111
      ConceptDecl *CD = CSE->getNamedConcept();
798
111
      SubNF = S.getNormalizedAssociatedConstraints(CD,
799
111
                                                   {CD->getConstraintExpr()});
800
111
      if (!SubNF)
801
1
        return None;
802
111
    }
803
804
110
    Optional<NormalizedConstraint> New;
805
110
    New.emplace(S.Context, *SubNF);
806
807
110
    if (substituteParameterMappings(
808
110
            S, *New, CSE->getNamedConcept(),
809
110
            CSE->getTemplateArguments(), CSE->getTemplateArgsAsWritten()))
810
1
      return None;
811
812
109
    return New;
813
110
  }
814
73
  return NormalizedConstraint{new (S.Context) AtomicConstraint(S, E)};
815
236
}
816
817
using NormalForm =
818
    llvm::SmallVector<llvm::SmallVector<AtomicConstraint *, 2>, 4>;
819
820
259
static NormalForm makeCNF(const NormalizedConstraint &Normalized) {
821
259
  if (Normalized.isAtomic())
822
186
    return {{Normalized.getAtomicConstraint()}};
823
824
73
  NormalForm LCNF = makeCNF(Normalized.getLHS());
825
73
  NormalForm RCNF = makeCNF(Normalized.getRHS());
826
73
  if (Normalized.getCompoundKind() == NormalizedConstraint::CCK_Conjunction) {
827
68
    LCNF.reserve(LCNF.size() + RCNF.size());
828
140
    while (!RCNF.empty())
829
72
      LCNF.push_back(RCNF.pop_back_val());
830
68
    return LCNF;
831
68
  }
832
833
  // Disjunction
834
5
  NormalForm Res;
835
5
  Res.reserve(LCNF.size() * RCNF.size());
836
5
  for (auto &LDisjunction : LCNF)
837
14
    
for (auto &RDisjunction : RCNF)7
{
838
14
      NormalForm::value_type Combined;
839
14
      Combined.reserve(LDisjunction.size() + RDisjunction.size());
840
14
      std::copy(LDisjunction.begin(), LDisjunction.end(),
841
14
                std::back_inserter(Combined));
842
14
      std::copy(RDisjunction.begin(), RDisjunction.end(),
843
14
                std::back_inserter(Combined));
844
14
      Res.emplace_back(Combined);
845
14
    }
846
5
  return Res;
847
73
}
848
849
261
static NormalForm makeDNF(const NormalizedConstraint &Normalized) {
850
261
  if (Normalized.isAtomic())
851
187
    return {{Normalized.getAtomicConstraint()}};
852
853
74
  NormalForm LDNF = makeDNF(Normalized.getLHS());
854
74
  NormalForm RDNF = makeDNF(Normalized.getRHS());
855
74
  if (Normalized.getCompoundKind() == NormalizedConstraint::CCK_Disjunction) {
856
5
    LDNF.reserve(LDNF.size() + RDNF.size());
857
10
    while (!RDNF.empty())
858
5
      LDNF.push_back(RDNF.pop_back_val());
859
5
    return LDNF;
860
5
  }
861
862
  // Conjunction
863
69
  NormalForm Res;
864
69
  Res.reserve(LDNF.size() * RDNF.size());
865
69
  for (auto &LConjunction : LDNF) {
866
69
    for (auto &RConjunction : RDNF) {
867
69
      NormalForm::value_type Combined;
868
69
      Combined.reserve(LConjunction.size() + RConjunction.size());
869
69
      std::copy(LConjunction.begin(), LConjunction.end(),
870
69
                std::back_inserter(Combined));
871
69
      std::copy(RConjunction.begin(), RConjunction.end(),
872
69
                std::back_inserter(Combined));
873
69
      Res.emplace_back(Combined);
874
69
    }
875
69
  }
876
69
  return Res;
877
74
}
878
879
template<typename AtomicSubsumptionEvaluator>
880
static bool subsumes(NormalForm PDNF, NormalForm QCNF,
881
139
                     AtomicSubsumptionEvaluator E) {
882
  // C++ [temp.constr.order] p2
883
  //   Then, P subsumes Q if and only if, for every disjunctive clause Pi in the
884
  //   disjunctive normal form of P, Pi subsumes every conjunctive clause Qj in
885
  //   the conjuctive normal form of Q, where [...]
886
141
  for (const auto &Pi : PDNF) {
887
195
    for (const auto &Qj : QCNF) {
888
      // C++ [temp.constr.order] p2
889
      //   - [...] a disjunctive clause Pi subsumes a conjunctive clause Qj if
890
      //     and only if there exists an atomic constraint Pia in Pi for which
891
      //     there exists an atomic constraint, Qjb, in Qj such that Pia
892
      //     subsumes Qjb.
893
195
      bool Found = false;
894
240
      for (const AtomicConstraint *Pia : Pi) {
895
242
        for (const AtomicConstraint *Qjb : Qj) {
896
242
          if (E(*Pia, *Qjb)) {
897
114
            Found = true;
898
114
            break;
899
114
          }
900
242
        }
901
240
        if (Found)
902
114
          break;
903
240
      }
904
195
      if (!Found)
905
81
        return false;
906
195
    }
907
141
  }
908
58
  return true;
909
139
}
SemaConcept.cpp:bool subsumes<clang::Sema::IsAtLeastAsConstrained(clang::NamedDecl*, llvm::ArrayRef<clang::Expr const*>, clang::NamedDecl*, llvm::ArrayRef<clang::Expr const*>, bool&)::$_2>(llvm::SmallVector<llvm::SmallVector<clang::AtomicConstraint*, 2u>, 4u>, llvm::SmallVector<llvm::SmallVector<clang::AtomicConstraint*, 2u>, 4u>, clang::Sema::IsAtLeastAsConstrained(clang::NamedDecl*, llvm::ArrayRef<clang::Expr const*>, clang::NamedDecl*, llvm::ArrayRef<clang::Expr const*>, bool&)::$_2)
Line
Count
Source
881
87
                     AtomicSubsumptionEvaluator E) {
882
  // C++ [temp.constr.order] p2
883
  //   Then, P subsumes Q if and only if, for every disjunctive clause Pi in the
884
  //   disjunctive normal form of P, Pi subsumes every conjunctive clause Qj in
885
  //   the conjuctive normal form of Q, where [...]
886
89
  for (const auto &Pi : PDNF) {
887
130
    for (const auto &Qj : QCNF) {
888
      // C++ [temp.constr.order] p2
889
      //   - [...] a disjunctive clause Pi subsumes a conjunctive clause Qj if
890
      //     and only if there exists an atomic constraint Pia in Pi for which
891
      //     there exists an atomic constraint, Qjb, in Qj such that Pia
892
      //     subsumes Qjb.
893
130
      bool Found = false;
894
162
      for (const AtomicConstraint *Pia : Pi) {
895
164
        for (const AtomicConstraint *Qjb : Qj) {
896
164
          if (E(*Pia, *Qjb)) {
897
82
            Found = true;
898
82
            break;
899
82
          }
900
164
        }
901
162
        if (Found)
902
82
          break;
903
162
      }
904
130
      if (!Found)
905
48
        return false;
906
130
    }
907
89
  }
908
39
  return true;
909
87
}
SemaConcept.cpp:bool subsumes<clang::Sema::MaybeEmitAmbiguousAtomicConstraintsDiagnostic(clang::NamedDecl*, llvm::ArrayRef<clang::Expr const*>, clang::NamedDecl*, llvm::ArrayRef<clang::Expr const*>)::$_3>(llvm::SmallVector<llvm::SmallVector<clang::AtomicConstraint*, 2u>, 4u>, llvm::SmallVector<llvm::SmallVector<clang::AtomicConstraint*, 2u>, 4u>, clang::Sema::MaybeEmitAmbiguousAtomicConstraintsDiagnostic(clang::NamedDecl*, llvm::ArrayRef<clang::Expr const*>, clang::NamedDecl*, llvm::ArrayRef<clang::Expr const*>)::$_3)
Line
Count
Source
881
26
                     AtomicSubsumptionEvaluator E) {
882
  // C++ [temp.constr.order] p2
883
  //   Then, P subsumes Q if and only if, for every disjunctive clause Pi in the
884
  //   disjunctive normal form of P, Pi subsumes every conjunctive clause Qj in
885
  //   the conjuctive normal form of Q, where [...]
886
26
  for (const auto &Pi : PDNF) {
887
30
    for (const auto &Qj : QCNF) {
888
      // C++ [temp.constr.order] p2
889
      //   - [...] a disjunctive clause Pi subsumes a conjunctive clause Qj if
890
      //     and only if there exists an atomic constraint Pia in Pi for which
891
      //     there exists an atomic constraint, Qjb, in Qj such that Pia
892
      //     subsumes Qjb.
893
30
      bool Found = false;
894
39
      for (const AtomicConstraint *Pia : Pi) {
895
39
        for (const AtomicConstraint *Qjb : Qj) {
896
39
          if (E(*Pia, *Qjb)) {
897
10
            Found = true;
898
10
            break;
899
10
          }
900
39
        }
901
39
        if (Found)
902
10
          break;
903
39
      }
904
30
      if (!Found)
905
20
        return false;
906
30
    }
907
26
  }
908
6
  return true;
909
26
}
SemaConcept.cpp:bool subsumes<clang::Sema::MaybeEmitAmbiguousAtomicConstraintsDiagnostic(clang::NamedDecl*, llvm::ArrayRef<clang::Expr const*>, clang::NamedDecl*, llvm::ArrayRef<clang::Expr const*>)::$_4>(llvm::SmallVector<llvm::SmallVector<clang::AtomicConstraint*, 2u>, 4u>, llvm::SmallVector<llvm::SmallVector<clang::AtomicConstraint*, 2u>, 4u>, clang::Sema::MaybeEmitAmbiguousAtomicConstraintsDiagnostic(clang::NamedDecl*, llvm::ArrayRef<clang::Expr const*>, clang::NamedDecl*, llvm::ArrayRef<clang::Expr const*>)::$_4)
Line
Count
Source
881
26
                     AtomicSubsumptionEvaluator E) {
882
  // C++ [temp.constr.order] p2
883
  //   Then, P subsumes Q if and only if, for every disjunctive clause Pi in the
884
  //   disjunctive normal form of P, Pi subsumes every conjunctive clause Qj in
885
  //   the conjuctive normal form of Q, where [...]
886
26
  for (const auto &Pi : PDNF) {
887
35
    for (const auto &Qj : QCNF) {
888
      // C++ [temp.constr.order] p2
889
      //   - [...] a disjunctive clause Pi subsumes a conjunctive clause Qj if
890
      //     and only if there exists an atomic constraint Pia in Pi for which
891
      //     there exists an atomic constraint, Qjb, in Qj such that Pia
892
      //     subsumes Qjb.
893
35
      bool Found = false;
894
39
      for (const AtomicConstraint *Pia : Pi) {
895
39
        for (const AtomicConstraint *Qjb : Qj) {
896
39
          if (E(*Pia, *Qjb)) {
897
22
            Found = true;
898
22
            break;
899
22
          }
900
39
        }
901
39
        if (Found)
902
22
          break;
903
39
      }
904
35
      if (!Found)
905
13
        return false;
906
35
    }
907
26
  }
908
13
  return true;
909
26
}
910
911
template<typename AtomicSubsumptionEvaluator>
912
static bool subsumes(Sema &S, NamedDecl *DP, ArrayRef<const Expr *> P,
913
                     NamedDecl *DQ, ArrayRef<const Expr *> Q, bool &Subsumes,
914
88
                     AtomicSubsumptionEvaluator E) {
915
  // C++ [temp.constr.order] p2
916
  //   In order to determine if a constraint P subsumes a constraint Q, P is
917
  //   transformed into disjunctive normal form, and Q is transformed into
918
  //   conjunctive normal form. [...]
919
88
  auto *PNormalized = S.getNormalizedAssociatedConstraints(DP, P);
920
88
  if (!PNormalized)
921
1
    return true;
922
87
  const NormalForm PDNF = makeDNF(*PNormalized);
923
924
87
  auto *QNormalized = S.getNormalizedAssociatedConstraints(DQ, Q);
925
87
  if (!QNormalized)
926
0
    return true;
927
87
  const NormalForm QCNF = makeCNF(*QNormalized);
928
929
87
  Subsumes = subsumes(PDNF, QCNF, E);
930
87
  return false;
931
87
}
932
933
bool Sema::IsAtLeastAsConstrained(NamedDecl *D1, ArrayRef<const Expr *> AC1,
934
                                  NamedDecl *D2, ArrayRef<const Expr *> AC2,
935
2.42k
                                  bool &Result) {
936
2.42k
  if (AC1.empty()) {
937
2.15k
    Result = AC2.empty();
938
2.15k
    return false;
939
2.15k
  }
940
272
  if (AC2.empty()) {
941
    // TD1 has associated constraints and TD2 does not.
942
27
    Result = true;
943
27
    return false;
944
27
  }
945
946
245
  std::pair<NamedDecl *, NamedDecl *> Key{D1, D2};
947
245
  auto CacheEntry = SubsumptionCache.find(Key);
948
245
  if (CacheEntry != SubsumptionCache.end()) {
949
157
    Result = CacheEntry->second;
950
157
    return false;
951
157
  }
952
953
88
  if (subsumes(*this, D1, AC1, D2, AC2, Result,
954
164
        [this] (const AtomicConstraint &A, const AtomicConstraint &B) {
955
164
          return A.subsumes(Context, B);
956
164
        }))
957
1
    return true;
958
87
  SubsumptionCache.try_emplace(Key, Result);
959
87
  return false;
960
88
}
961
962
bool Sema::MaybeEmitAmbiguousAtomicConstraintsDiagnostic(NamedDecl *D1,
963
372
    ArrayRef<const Expr *> AC1, NamedDecl *D2, ArrayRef<const Expr *> AC2) {
964
372
  if (isSFINAEContext())
965
    // No need to work here because our notes would be discarded.
966
0
    return false;
967
968
372
  if (AC1.empty() || 
AC2.empty()14
)
969
358
    return false;
970
971
14
  auto NormalExprEvaluator =
972
39
      [this] (const AtomicConstraint &A, const AtomicConstraint &B) {
973
39
        return A.subsumes(Context, B);
974
39
      };
975
976
14
  const Expr *AmbiguousAtomic1 = nullptr, *AmbiguousAtomic2 = nullptr;
977
14
  auto IdenticalExprEvaluator =
978
39
      [&] (const AtomicConstraint &A, const AtomicConstraint &B) {
979
39
        if (!A.hasMatchingParameterMapping(Context, B))
980
9
          return false;
981
30
        const Expr *EA = A.ConstraintExpr, *EB = B.ConstraintExpr;
982
30
        if (EA == EB)
983
10
          return true;
984
985
        // Not the same source level expression - are the expressions
986
        // identical?
987
20
        llvm::FoldingSetNodeID IDA, IDB;
988
20
        EA->Profile(IDA, Context, /*Cannonical=*/true);
989
20
        EB->Profile(IDB, Context, /*Cannonical=*/true);
990
20
        if (IDA != IDB)
991
8
          return false;
992
993
12
        AmbiguousAtomic1 = EA;
994
12
        AmbiguousAtomic2 = EB;
995
12
        return true;
996
20
      };
997
998
14
  {
999
    // The subsumption checks might cause diagnostics
1000
14
    SFINAETrap Trap(*this);
1001
14
    auto *Normalized1 = getNormalizedAssociatedConstraints(D1, AC1);
1002
14
    if (!Normalized1)
1003
1
      return false;
1004
13
    const NormalForm DNF1 = makeDNF(*Normalized1);
1005
13
    const NormalForm CNF1 = makeCNF(*Normalized1);
1006
1007
13
    auto *Normalized2 = getNormalizedAssociatedConstraints(D2, AC2);
1008
13
    if (!Normalized2)
1009
0
      return false;
1010
13
    const NormalForm DNF2 = makeDNF(*Normalized2);
1011
13
    const NormalForm CNF2 = makeCNF(*Normalized2);
1012
1013
13
    bool Is1AtLeastAs2Normally = subsumes(DNF1, CNF2, NormalExprEvaluator);
1014
13
    bool Is2AtLeastAs1Normally = subsumes(DNF2, CNF1, NormalExprEvaluator);
1015
13
    bool Is1AtLeastAs2 = subsumes(DNF1, CNF2, IdenticalExprEvaluator);
1016
13
    bool Is2AtLeastAs1 = subsumes(DNF2, CNF1, IdenticalExprEvaluator);
1017
13
    if (Is1AtLeastAs2 == Is1AtLeastAs2Normally &&
1018
13
        
Is2AtLeastAs1 == Is2AtLeastAs1Normally7
)
1019
      // Same result - no ambiguity was caused by identical atomic expressions.
1020
7
      return false;
1021
13
  }
1022
1023
  // A different result! Some ambiguous atomic constraint(s) caused a difference
1024
6
  assert(AmbiguousAtomic1 && AmbiguousAtomic2);
1025
1026
0
  Diag(AmbiguousAtomic1->getBeginLoc(), diag::note_ambiguous_atomic_constraints)
1027
6
      << AmbiguousAtomic1->getSourceRange();
1028
6
  Diag(AmbiguousAtomic2->getBeginLoc(),
1029
6
       diag::note_ambiguous_atomic_constraints_similar_expression)
1030
6
      << AmbiguousAtomic2->getSourceRange();
1031
6
  return true;
1032
13
}
1033
1034
concepts::ExprRequirement::ExprRequirement(
1035
    Expr *E, bool IsSimple, SourceLocation NoexceptLoc,
1036
    ReturnTypeRequirement Req, SatisfactionStatus Status,
1037
    ConceptSpecializationExpr *SubstitutedConstraintExpr) :
1038
    Requirement(IsSimple ? RK_Simple : RK_Compound, Status == SS_Dependent,
1039
                Status == SS_Dependent &&
1040
                (E->containsUnexpandedParameterPack() ||
1041
                 Req.containsUnexpandedParameterPack()),
1042
                Status == SS_Satisfied), Value(E), NoexceptLoc(NoexceptLoc),
1043
    TypeReq(Req), SubstitutedConstraintExpr(SubstitutedConstraintExpr),
1044
192
    Status(Status) {
1045
192
  assert((!IsSimple || (Req.isEmpty() && NoexceptLoc.isInvalid())) &&
1046
192
         "Simple requirement must not have a return type requirement or a "
1047
192
         "noexcept specification");
1048
0
  assert((Status > SS_TypeRequirementSubstitutionFailure && Req.isTypeConstraint()) ==
1049
192
         (SubstitutedConstraintExpr != nullptr));
1050
192
}
1051
1052
concepts::ExprRequirement::ExprRequirement(
1053
    SubstitutionDiagnostic *ExprSubstDiag, bool IsSimple,
1054
    SourceLocation NoexceptLoc, ReturnTypeRequirement Req) :
1055
    Requirement(IsSimple ? RK_Simple : RK_Compound, Req.isDependent(),
1056
                Req.containsUnexpandedParameterPack(), /*IsSatisfied=*/false),
1057
    Value(ExprSubstDiag), NoexceptLoc(NoexceptLoc), TypeReq(Req),
1058
28
    Status(SS_ExprSubstitutionFailure) {
1059
28
  assert((!IsSimple || (Req.isEmpty() && NoexceptLoc.isInvalid())) &&
1060
28
         "Simple requirement must not have a return type requirement or a "
1061
28
         "noexcept specification");
1062
28
}
1063
1064
concepts::ExprRequirement::ReturnTypeRequirement::
1065
ReturnTypeRequirement(TemplateParameterList *TPL) :
1066
55
    TypeConstraintInfo(TPL, 0) {
1067
55
  assert(TPL->size() == 1);
1068
0
  const TypeConstraint *TC =
1069
55
      cast<TemplateTypeParmDecl>(TPL->getParam(0))->getTypeConstraint();
1070
55
  assert(TC &&
1071
55
         "TPL must have a template type parameter with a type constraint");
1072
0
  auto *Constraint =
1073
55
      cast_or_null<ConceptSpecializationExpr>(
1074
55
          TC->getImmediatelyDeclaredConstraint());
1075
55
  bool Dependent =
1076
55
      Constraint->getTemplateArgsAsWritten() &&
1077
55
      TemplateSpecializationType::anyInstantiationDependentTemplateArguments(
1078
55
          Constraint->getTemplateArgsAsWritten()->arguments().drop_front(1));
1079
55
  TypeConstraintInfo.setInt(Dependent ? 
111
:
044
);
1080
55
}
1081
1082
concepts::TypeRequirement::TypeRequirement(TypeSourceInfo *T) :
1083
    Requirement(RK_Type, T->getType()->isInstantiationDependentType(),
1084
                T->getType()->containsUnexpandedParameterPack(),
1085
                // We reach this ctor with either dependent types (in which
1086
                // IsSatisfied doesn't matter) or with non-dependent type in
1087
                // which the existence of the type indicates satisfaction.
1088
                /*IsSatisfied=*/true),
1089
    Value(T),
1090
    Status(T->getType()->isInstantiationDependentType() ? SS_Dependent
1091
74
                                                        : SS_Satisfied) {}