summaryrefslogtreecommitdiffstats
path: root/clang/lib/Serialization/ASTWriterStmt.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'clang/lib/Serialization/ASTWriterStmt.cpp')
-rw-r--r--clang/lib/Serialization/ASTWriterStmt.cpp105
1 files changed, 92 insertions, 13 deletions
diff --git a/clang/lib/Serialization/ASTWriterStmt.cpp b/clang/lib/Serialization/ASTWriterStmt.cpp
index 9231f3b2b9b..1b118c257a4 100644
--- a/clang/lib/Serialization/ASTWriterStmt.cpp
+++ b/clang/lib/Serialization/ASTWriterStmt.cpp
@@ -12,6 +12,7 @@
//===----------------------------------------------------------------------===//
#include "clang/Serialization/ASTRecordWriter.h"
+#include "clang/Sema/DeclSpec.h"
#include "clang/AST/ASTContext.h"
#include "clang/AST/DeclCXX.h"
#include "clang/AST/DeclObjC.h"
@@ -388,19 +389,9 @@ void ASTStmtWriter::VisitDependentCoawaitExpr(DependentCoawaitExpr *E) {
Code = serialization::EXPR_DEPENDENT_COAWAIT;
}
-void ASTStmtWriter::VisitConceptSpecializationExpr(
- ConceptSpecializationExpr *E) {
- VisitExpr(E);
- ArrayRef<TemplateArgument> TemplateArgs = E->getTemplateArguments();
- Record.push_back(TemplateArgs.size());
- Record.AddNestedNameSpecifierLoc(E->getNestedNameSpecifierLoc());
- Record.AddSourceLocation(E->getTemplateKWLoc());
- Record.AddDeclarationNameInfo(E->getConceptNameInfo());
- Record.AddDeclRef(E->getNamedConcept());
- Record.AddASTTemplateArgumentListInfo(E->getTemplateArgsAsWritten());
- for (const TemplateArgument &Arg : TemplateArgs)
- Record.AddTemplateArgument(Arg);
- const ASTConstraintSatisfaction &Satisfaction = E->getSatisfaction();
+static void
+addConstraintSatisfaction(ASTRecordWriter &Record,
+ const ASTConstraintSatisfaction &Satisfaction) {
Record.push_back(Satisfaction.IsSatisfied);
if (!Satisfaction.IsSatisfied) {
Record.push_back(Satisfaction.NumRecords);
@@ -418,10 +409,98 @@ void ASTStmtWriter::VisitConceptSpecializationExpr(
}
}
}
+}
+
+static void
+addSubstitutionDiagnostic(
+ ASTRecordWriter &Record,
+ const concepts::Requirement::SubstitutionDiagnostic *D) {
+ Record.AddString(D->SubstitutedEntity);
+ Record.AddSourceLocation(D->DiagLoc);
+ Record.AddString(D->DiagMessage);
+}
+
+void ASTStmtWriter::VisitConceptSpecializationExpr(
+ ConceptSpecializationExpr *E) {
+ VisitExpr(E);
+ ArrayRef<TemplateArgument> TemplateArgs = E->getTemplateArguments();
+ Record.push_back(TemplateArgs.size());
+ Record.AddNestedNameSpecifierLoc(E->getNestedNameSpecifierLoc());
+ Record.AddSourceLocation(E->getTemplateKWLoc());
+ Record.AddDeclarationNameInfo(E->getConceptNameInfo());
+ Record.AddDeclRef(E->getNamedConcept());
+ Record.AddASTTemplateArgumentListInfo(E->getTemplateArgsAsWritten());
+ for (const TemplateArgument &Arg : TemplateArgs)
+ Record.AddTemplateArgument(Arg);
+ if (!E->isValueDependent())
+ addConstraintSatisfaction(Record, E->getSatisfaction());
Code = serialization::EXPR_CONCEPT_SPECIALIZATION;
}
+void ASTStmtWriter::VisitRequiresExpr(RequiresExpr *E) {
+ VisitExpr(E);
+ Record.push_back(E->getLocalParameters().size());
+ Record.push_back(E->getRequirements().size());
+ Record.AddSourceLocation(E->RequiresExprBits.RequiresKWLoc);
+ Record.push_back(E->RequiresExprBits.IsSatisfied);
+ Record.AddDeclRef(E->getBody());
+ for (ParmVarDecl *P : E->getLocalParameters())
+ Record.AddDeclRef(P);
+ for (concepts::Requirement *R : E->getRequirements()) {
+ if (auto *TypeReq = dyn_cast<concepts::TypeRequirement>(R)) {
+ Record.push_back(concepts::Requirement::RK_Type);
+ Record.push_back(TypeReq->Status);
+ if (TypeReq->Status == concepts::TypeRequirement::SS_SubstitutionFailure)
+ addSubstitutionDiagnostic(Record, TypeReq->getSubstitutionDiagnostic());
+ else
+ Record.AddTypeSourceInfo(TypeReq->getType());
+ } else if (auto *ExprReq = dyn_cast<concepts::ExprRequirement>(R)) {
+ Record.push_back(ExprReq->getKind());
+ Record.push_back(ExprReq->Status);
+ if (ExprReq->isExprSubstitutionFailure()) {
+ addSubstitutionDiagnostic(Record,
+ ExprReq->Value.get<concepts::Requirement::SubstitutionDiagnostic *>());
+ } else
+ Record.AddStmt(ExprReq->Value.get<Expr *>());
+ if (ExprReq->getKind() == concepts::Requirement::RK_Compound) {
+ Record.AddSourceLocation(ExprReq->NoexceptLoc);
+ const auto &RetReq = ExprReq->getReturnTypeRequirement();
+ if (RetReq.isSubstitutionFailure()) {
+ Record.push_back(2);
+ addSubstitutionDiagnostic(Record, RetReq.getSubstitutionDiagnostic());
+ } else if (RetReq.isTypeConstraint()) {
+ Record.push_back(1);
+ Record.AddTemplateParameterList(
+ RetReq.getTypeConstraintTemplateParameterList());
+ if (ExprReq->Status >=
+ concepts::ExprRequirement::SS_ConstraintsNotSatisfied)
+ Record.AddStmt(
+ ExprReq->getReturnTypeRequirementSubstitutedConstraintExpr());
+ } else {
+ assert(RetReq.isEmpty());
+ Record.push_back(0);
+ }
+ }
+ } else {
+ auto *NestedReq = cast<concepts::NestedRequirement>(R);
+ Record.push_back(concepts::Requirement::RK_Nested);
+ Record.push_back(NestedReq->isSubstitutionFailure());
+ if (NestedReq->isSubstitutionFailure()){
+ addSubstitutionDiagnostic(Record,
+ NestedReq->getSubstitutionDiagnostic());
+ } else {
+ Record.AddStmt(NestedReq->Value.get<Expr *>());
+ if (!NestedReq->isDependent())
+ addConstraintSatisfaction(Record, *NestedReq->Satisfaction);
+ }
+ }
+ }
+ Record.AddSourceLocation(E->getEndLoc());
+
+ Code = serialization::EXPR_REQUIRES;
+}
+
void ASTStmtWriter::VisitCapturedStmt(CapturedStmt *S) {
VisitStmt(S);
OpenPOWER on IntegriCloud