jcking1034 updated this revision to Diff 387769.
jcking1034 added a comment.

Improve wrapping of PolymorphicMatchers


Repository:
  rG LLVM Github Monorepo

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D113943/new/

https://reviews.llvm.org/D113943

Files:
  clang/include/clang/ASTMatchers/ASTMatchers.h
  clang/include/clang/ASTMatchers/ASTMatchersInternal.h

Index: clang/include/clang/ASTMatchers/ASTMatchersInternal.h
===================================================================
--- clang/include/clang/ASTMatchers/ASTMatchersInternal.h
+++ clang/include/clang/ASTMatchers/ASTMatchersInternal.h
@@ -43,6 +43,7 @@
 #include "clang/AST/ExprCXX.h"
 #include "clang/AST/ExprObjC.h"
 #include "clang/AST/NestedNameSpecifier.h"
+#include "clang/AST/PrettyPrinter.h"
 #include "clang/AST/Stmt.h"
 #include "clang/AST/TemplateName.h"
 #include "clang/AST/Type.h"
@@ -1042,6 +1043,44 @@
   std::vector<std::string> Names;
 };
 
+template <typename T> class WithTagMatcher : public MatcherInterface<T> {
+public:
+  explicit WithTagMatcher(std::string _BeforeTag, std::string _AfterTag,
+                          internal::Matcher<T> _InnerMatcher)
+      : BeforeTag(std::move(_BeforeTag)), AfterTag(std::move(_AfterTag)),
+        InnerMatcher(_InnerMatcher) {}
+  explicit WithTagMatcher(internal::Matcher<T> _InnerMatcher)
+      : BeforeTag("⭐ Attempting new match"),
+        AfterTag("✔️ Concluding attempt"), InnerMatcher(_InnerMatcher) {}
+  bool matches(const T &Node, ASTMatchFinder *Finder,
+               BoundNodesTreeBuilder *Builder) const override {
+    DynTypedNode DTN = DynTypedNode::create(Node);
+
+    llvm::errs() << BeforeTag << "\n";
+
+    llvm::errs() << "Matcher Name: " << InnerMatcher.getMatcherName() << "\n";
+
+    llvm::errs() << "Node Kind: " << DTN.getNodeKind().asStringRef() << "\n"
+                 << "Node Value:\n```\n";
+    DTN.print(llvm::errs(), PrintingPolicy(LangOptions()));
+    llvm::errs() << "\n```\n"
+                 << "Node AST:\n";
+    DTN.dump(llvm::errs(), Finder->getASTContext());
+
+    bool result = InnerMatcher.matches(Node, Finder, Builder);
+    llvm::errs() << "Result: " << (result ? "Successful\n" : "Unsuccessful\n");
+
+    llvm::errs() << AfterTag << "\n\n";
+
+    return result;
+  }
+
+private:
+  std::string BeforeTag;
+  std::string AfterTag;
+  internal::Matcher<T> InnerMatcher;
+};
+
 /// Matches named declarations with a specific name.
 ///
 /// See \c hasName() and \c hasAnyName() in ASTMatchers.h for details.
@@ -1718,6 +1757,38 @@
   std::tuple<ParamTypes...> Params;
 };
 
+template <template <typename T, typename... Params> class MatcherT,
+          typename ReturnTypesF, typename... ParamTypes>
+class PolymorphicWithTagMatcher {
+public:
+  PolymorphicWithTagMatcher(
+      internal::PolymorphicMatcher<MatcherT, ReturnTypesF, ParamTypes...>
+          _InnerMatcher)
+      : InnerMatcher(_InnerMatcher) {}
+
+  using ReturnTypes = typename ExtractFunctionArgMeta<ReturnTypesF>::type;
+
+  template <typename T> operator Matcher<T>() const LLVM_LVALUE_FUNCTION {
+    static_assert(TypeListContainsSuperOf<ReturnTypes, T>::value,
+                  "right polymorphic conversion");
+    return internal::Matcher<T>(
+        new internal::WithTagMatcher<T>(internal::Matcher<T>(InnerMatcher)));
+  }
+
+#if LLVM_HAS_RVALUE_REFERENCE_THIS
+  template <typename T> operator Matcher<T>() && {
+    static_assert(TypeListContainsSuperOf<ReturnTypes, T>::value,
+                  "right polymorphic conversion");
+    return internal::Matcher<T>(new internal::WithTagMatcher<T>(
+        internal::Matcher<T>(std::move(InnerMatcher))));
+  }
+#endif
+
+private:
+  internal::PolymorphicMatcher<MatcherT, ReturnTypesF, ParamTypes...>
+      InnerMatcher;
+};
+
 /// Matches nodes of type T that have child nodes of type ChildT for
 /// which a specified child matcher matches.
 ///
Index: clang/include/clang/ASTMatchers/ASTMatchers.h
===================================================================
--- clang/include/clang/ASTMatchers/ASTMatchers.h
+++ clang/include/clang/ASTMatchers/ASTMatchers.h
@@ -2993,6 +2993,40 @@
       new internal::HasNameMatcher({std::string(Name)}));
 }
 
+template <typename T>
+inline internal::Matcher<T> withTag(std::string BeforeTag, std::string AfterTag,
+                                    const internal::Matcher<T> &InnerMatcher) {
+  return internal::Matcher<T>(
+      new internal::WithTagMatcher<T>(BeforeTag, AfterTag, InnerMatcher));
+}
+
+template <typename T, template <typename, typename... Params> class MatcherT,
+          typename ReturnTypesF, typename... ParamTypes>
+inline internal::PolymorphicWithTagMatcher<MatcherT, ReturnTypesF,
+                                           ParamTypes...>
+withTag(std::string BeforeTag, std::string AfterTag,
+        const internal::PolymorphicMatcher<MatcherT, ReturnTypesF,
+                                           ParamTypes...> &InnerMatcher) {
+  return internal::PolymorphicWithTagMatcher<MatcherT, ReturnTypesF,
+                                             ParamTypes...>(BeforeTag, AfterTag,
+                                                            InnerMatcher);
+}
+
+template <typename T>
+inline internal::Matcher<T> withTag(const internal::Matcher<T> &InnerMatcher) {
+  return internal::Matcher<T>(new internal::WithTagMatcher<T>(InnerMatcher));
+}
+
+template <template <typename, typename... Params> class MatcherT,
+          typename ReturnTypesF, typename... ParamTypes>
+inline internal::PolymorphicWithTagMatcher<MatcherT, ReturnTypesF,
+                                           ParamTypes...>
+withTag(const internal::PolymorphicMatcher<MatcherT, ReturnTypesF,
+                                           ParamTypes...> &InnerMatcher) {
+  return internal::PolymorphicWithTagMatcher<MatcherT, ReturnTypesF,
+                                             ParamTypes...>(InnerMatcher);
+}
+
 /// Matches NamedDecl nodes that have any of the specified names.
 ///
 /// This matcher is only provided as a performance optimization of hasName.
_______________________________________________
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits

Reply via email to