diff options
author | Erich Keane <erich.keane@intel.com> | 2022-07-22 13:04:59 -0700 |
---|---|---|
committer | Erich Keane <erich.keane@intel.com> | 2022-07-22 13:05:42 -0700 |
commit | 0b36a62d5f3505e21692ae0abf25ef00836329e3 (patch) | |
tree | b2378f73693690b650d438271dc49023369a2469 /clang/include | |
parent | b95d31a849b91650367ee205eac5af8750cccf3e (diff) | |
download | llvm-0b36a62d5f3505e21692ae0abf25ef00836329e3.zip llvm-0b36a62d5f3505e21692ae0abf25ef00836329e3.tar.gz llvm-0b36a62d5f3505e21692ae0abf25ef00836329e3.tar.bz2 |
[NFC] Add some additional features to MultiLevelTemplateArgumentList
These are useful when dealing with multi-depth instantiation in deferred
concepts, so this is split off of that patch.
Diffstat (limited to 'clang/include')
-rw-r--r-- | clang/include/clang/Sema/Template.h | 34 |
1 files changed, 34 insertions, 0 deletions
diff --git a/clang/include/clang/Sema/Template.h b/clang/include/clang/Sema/Template.h index 5dcde77..495555b 100644 --- a/clang/include/clang/Sema/Template.h +++ b/clang/include/clang/Sema/Template.h @@ -75,6 +75,8 @@ enum class TemplateSubstitutionKind : char { class MultiLevelTemplateArgumentList { /// The template argument list at a certain template depth using ArgList = ArrayRef<TemplateArgument>; + using ArgListsIterator = SmallVector<ArgList, 4>::iterator; + using ConstArgListsIterator = SmallVector<ArgList, 4>::const_iterator; /// The template argument lists, stored from the innermost template /// argument list (first) to the outermost template argument list (last). @@ -121,6 +123,12 @@ enum class TemplateSubstitutionKind : char { return TemplateArgumentLists.size(); } + // Determine the number of substituted args at 'Depth'. + unsigned getNumSubsitutedArgs(unsigned Depth) const { + assert(NumretainedOuterLevels <= Depth && Depth < getNumLevels()); + return TemplateArgumentLists[getNumLevels() - Depth - 1].size(); + } + unsigned getNumRetainedOuterLevels() const { return NumRetainedOuterLevels; } @@ -158,6 +166,14 @@ enum class TemplateSubstitutionKind : char { return !(*this)(Depth, Index).isNull(); } + bool isAnyArgInstantiationDependent() const { + for (ArgList List : TemplateArgumentLists) + for (const TemplateArgument &TA : List) + if (TA.isInstantiationDependent()) + return true; + return false; + } + /// Clear out a specific template argument. void setArgument(unsigned Depth, unsigned Index, TemplateArgument Arg) { @@ -183,6 +199,14 @@ enum class TemplateSubstitutionKind : char { TemplateArgumentLists.push_back(Args); } + /// Replaces the current 'innermost' level with the provided argument list. + /// This is useful for type deduction cases where we need to get the entire + /// list from the AST, but then add the deduced innermost list. + void replaceInnermostTemplateArguments(ArgList Args) { + assert(TemplateArgumentLists.size() > 0 && "Replacing in an empty list?"); + TemplateArgumentLists[0] = Args; + } + /// Add an outermost level that we are not substituting. We have no /// arguments at this level, and do not remove it from the depth of inner /// template parameters that we instantiate. @@ -197,6 +221,16 @@ enum class TemplateSubstitutionKind : char { const ArgList &getInnermost() const { return TemplateArgumentLists.front(); } + /// Retrieve the outermost template argument list. + const ArgList &getOutermost() const { + return TemplateArgumentLists.back(); + } + ArgListsIterator begin() { return TemplateArgumentLists.begin(); } + ConstArgListsIterator begin() const { + return TemplateArgumentLists.begin(); + } + ArgListsIterator end() { return TemplateArgumentLists.end(); } + ConstArgListsIterator end() const { return TemplateArgumentLists.end(); } }; /// The context in which partial ordering of function templates occurs. |