xref: /llvm-project/clang/lib/AST/ASTConcept.cpp (revision 63d9ef5e37539b8920eb6c93524e4be2c33a510c)
1fdf80e86SSaar Raz //===--- ASTConcept.cpp - Concepts Related AST Data Structures --*- C++ -*-===//
2fdf80e86SSaar Raz //
3c874dd53SChristopher Di Bella // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4c874dd53SChristopher Di Bella // See https://llvm.org/LICENSE.txt for license information.
5c874dd53SChristopher Di Bella // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6fdf80e86SSaar Raz //
7fdf80e86SSaar Raz //===----------------------------------------------------------------------===//
8fdf80e86SSaar Raz ///
9fdf80e86SSaar Raz /// \file
10fdf80e86SSaar Raz /// \brief This file defines AST data structures related to concepts.
11fdf80e86SSaar Raz ///
12fdf80e86SSaar Raz //===----------------------------------------------------------------------===//
13fdf80e86SSaar Raz 
14fdf80e86SSaar Raz #include "clang/AST/ASTConcept.h"
15fdf80e86SSaar Raz #include "clang/AST/ASTContext.h"
1667136522SBill Wendling #include "clang/AST/PrettyPrinter.h"
17099c1527SHaojian Wu #include "llvm/ADT/StringExtras.h"
1867136522SBill Wendling 
19fdf80e86SSaar Raz using namespace clang;
20fdf80e86SSaar Raz 
21fb196495SYounan Zhang static void
22fb196495SYounan Zhang CreateUnsatisfiedConstraintRecord(const ASTContext &C,
23fb196495SYounan Zhang                                   const UnsatisfiedConstraintRecord &Detail,
24b3ce8728SUtkarsh Saxena                                   UnsatisfiedConstraintRecord *TrailingObject) {
25*63d9ef5eSKazu Hirata   if (auto *E = dyn_cast<Expr *>(Detail))
26*63d9ef5eSKazu Hirata     new (TrailingObject) UnsatisfiedConstraintRecord(E);
27fdf80e86SSaar Raz   else {
28fdf80e86SSaar Raz     auto &SubstitutionDiagnostic =
29*63d9ef5eSKazu Hirata         *cast<std::pair<SourceLocation, StringRef> *>(Detail);
300998e3c4SYoungsuk Kim     StringRef Message = C.backupStr(SubstitutionDiagnostic.second);
31fdf80e86SSaar Raz     auto *NewSubstDiag = new (C) std::pair<SourceLocation, StringRef>(
320998e3c4SYoungsuk Kim         SubstitutionDiagnostic.first, Message);
33fb196495SYounan Zhang     new (TrailingObject) UnsatisfiedConstraintRecord(NewSubstDiag);
34fdf80e86SSaar Raz   }
35fdf80e86SSaar Raz }
36b3ce8728SUtkarsh Saxena 
37b3ce8728SUtkarsh Saxena ASTConstraintSatisfaction::ASTConstraintSatisfaction(
38b3ce8728SUtkarsh Saxena     const ASTContext &C, const ConstraintSatisfaction &Satisfaction)
39b3ce8728SUtkarsh Saxena     : NumRecords{Satisfaction.Details.size()},
40b3ce8728SUtkarsh Saxena       IsSatisfied{Satisfaction.IsSatisfied}, ContainsErrors{
41b3ce8728SUtkarsh Saxena                                                  Satisfaction.ContainsErrors} {
42b3ce8728SUtkarsh Saxena   for (unsigned I = 0; I < NumRecords; ++I)
43fb196495SYounan Zhang     CreateUnsatisfiedConstraintRecord(
44b3ce8728SUtkarsh Saxena         C, Satisfaction.Details[I],
45b3ce8728SUtkarsh Saxena         getTrailingObjects<UnsatisfiedConstraintRecord>() + I);
46b3ce8728SUtkarsh Saxena }
47b3ce8728SUtkarsh Saxena 
48b3ce8728SUtkarsh Saxena ASTConstraintSatisfaction::ASTConstraintSatisfaction(
49b3ce8728SUtkarsh Saxena     const ASTContext &C, const ASTConstraintSatisfaction &Satisfaction)
50b3ce8728SUtkarsh Saxena     : NumRecords{Satisfaction.NumRecords},
51b3ce8728SUtkarsh Saxena       IsSatisfied{Satisfaction.IsSatisfied},
52b3ce8728SUtkarsh Saxena       ContainsErrors{Satisfaction.ContainsErrors} {
53b3ce8728SUtkarsh Saxena   for (unsigned I = 0; I < NumRecords; ++I)
54fb196495SYounan Zhang     CreateUnsatisfiedConstraintRecord(
55b3ce8728SUtkarsh Saxena         C, *(Satisfaction.begin() + I),
56b3ce8728SUtkarsh Saxena         getTrailingObjects<UnsatisfiedConstraintRecord>() + I);
57fdf80e86SSaar Raz }
58fdf80e86SSaar Raz 
59fdf80e86SSaar Raz ASTConstraintSatisfaction *
60fdf80e86SSaar Raz ASTConstraintSatisfaction::Create(const ASTContext &C,
61fdf80e86SSaar Raz                                   const ConstraintSatisfaction &Satisfaction) {
62fdf80e86SSaar Raz   std::size_t size =
63fdf80e86SSaar Raz       totalSizeToAlloc<UnsatisfiedConstraintRecord>(
64fdf80e86SSaar Raz           Satisfaction.Details.size());
65fdf80e86SSaar Raz   void *Mem = C.Allocate(size, alignof(ASTConstraintSatisfaction));
66fdf80e86SSaar Raz   return new (Mem) ASTConstraintSatisfaction(C, Satisfaction);
67fdf80e86SSaar Raz }
68b933d37cSSaar Raz 
69b3ce8728SUtkarsh Saxena ASTConstraintSatisfaction *ASTConstraintSatisfaction::Rebuild(
70b3ce8728SUtkarsh Saxena     const ASTContext &C, const ASTConstraintSatisfaction &Satisfaction) {
71b3ce8728SUtkarsh Saxena   std::size_t size =
72b3ce8728SUtkarsh Saxena       totalSizeToAlloc<UnsatisfiedConstraintRecord>(Satisfaction.NumRecords);
73b3ce8728SUtkarsh Saxena   void *Mem = C.Allocate(size, alignof(ASTConstraintSatisfaction));
74b3ce8728SUtkarsh Saxena   return new (Mem) ASTConstraintSatisfaction(C, Satisfaction);
75b3ce8728SUtkarsh Saxena }
76b3ce8728SUtkarsh Saxena 
77b933d37cSSaar Raz void ConstraintSatisfaction::Profile(
78713562f5SSaar Raz     llvm::FoldingSetNodeID &ID, const ASTContext &C,
79713562f5SSaar Raz     const NamedDecl *ConstraintOwner, ArrayRef<TemplateArgument> TemplateArgs) {
80b933d37cSSaar Raz   ID.AddPointer(ConstraintOwner);
81b933d37cSSaar Raz   ID.AddInteger(TemplateArgs.size());
82b933d37cSSaar Raz   for (auto &Arg : TemplateArgs)
83b933d37cSSaar Raz     Arg.Profile(ID, C);
84b933d37cSSaar Raz }
8567136522SBill Wendling 
8667136522SBill Wendling ConceptReference *
8767136522SBill Wendling ConceptReference::Create(const ASTContext &C, NestedNameSpecifierLoc NNS,
8867136522SBill Wendling                          SourceLocation TemplateKWLoc,
8967136522SBill Wendling                          DeclarationNameInfo ConceptNameInfo,
9067136522SBill Wendling                          NamedDecl *FoundDecl, ConceptDecl *NamedConcept,
9167136522SBill Wendling                          const ASTTemplateArgumentListInfo *ArgsAsWritten) {
9267136522SBill Wendling   return new (C) ConceptReference(NNS, TemplateKWLoc, ConceptNameInfo,
9367136522SBill Wendling                                   FoundDecl, NamedConcept, ArgsAsWritten);
9467136522SBill Wendling }
9567136522SBill Wendling 
9667136522SBill Wendling void ConceptReference::print(llvm::raw_ostream &OS,
9767136522SBill Wendling                              const PrintingPolicy &Policy) const {
9867136522SBill Wendling   if (NestedNameSpec)
9967136522SBill Wendling     NestedNameSpec.getNestedNameSpecifier()->print(OS, Policy);
10067136522SBill Wendling   ConceptName.printName(OS, Policy);
10167136522SBill Wendling   if (hasExplicitTemplateArgs()) {
10267136522SBill Wendling     OS << "<";
103099c1527SHaojian Wu     llvm::ListSeparator Sep(", ");
10467136522SBill Wendling     // FIXME: Find corresponding parameter for argument
105099c1527SHaojian Wu     for (auto &ArgLoc : ArgsAsWritten->arguments()) {
106099c1527SHaojian Wu       OS << Sep;
10767136522SBill Wendling       ArgLoc.getArgument().print(Policy, OS, /*IncludeType*/ false);
108099c1527SHaojian Wu     }
10967136522SBill Wendling     OS << ">";
11067136522SBill Wendling   }
11167136522SBill Wendling }
112