diff --git a/clang/include/clang/AST/RecursiveASTVisitor.h b/clang/include/clang/AST/RecursiveASTVisitor.h --- a/clang/include/clang/AST/RecursiveASTVisitor.h +++ b/clang/include/clang/AST/RecursiveASTVisitor.h @@ -331,6 +331,31 @@ struct has_same_member_pointer_type : std::true_type {}; + template struct is_same_method_impl { + static bool isSameMethod(...) { return false; } + }; + + template <> struct is_same_method_impl { + template + static bool + isSameMethod(FirstResult (FirstTy::*FirstMethodPtr)(FirstParams...), + SecondResult (SecondTy::*SecondMethodPtr)(SecondParams...)) { + return FirstMethodPtr == SecondMethodPtr; + } + }; + + /// Returns true if and only if \p FirstMethodPtr and \p SecondMethodPtr + /// are pointers to the same non-static member function. + template + bool isSameMethod(FirstMethodPtrTy FirstMethodPtr, + SecondMethodPtrTy SecondMethodPtr) { + return is_same_method_impl< + has_same_member_pointer_type:: + value>::isSameMethod(FirstMethodPtr, SecondMethodPtr); + } + // Traverse the given statement. If the most-derived traverse function takes a // data recursion queue, pass it on; otherwise, discard it. Note that the // first branch of this conditional must compile whether or not the derived @@ -609,17 +634,22 @@ #define ABSTRACT_STMT(STMT) #define STMT(CLASS, PARENT) \ case Stmt::CLASS##Class: \ - TRY_TO(WalkUpFrom##CLASS(static_cast(S))); break; + if (isSameMethod(&RecursiveASTVisitor::Traverse##CLASS, \ + &Derived::Traverse##CLASS)) { \ + TRY_TO(WalkUpFrom##CLASS(static_cast(S))); \ + } \ + break; #define INITLISTEXPR(CLASS, PARENT) \ case Stmt::CLASS##Class: \ - { \ + if (isSameMethod(&RecursiveASTVisitor::Traverse##CLASS, \ + &Derived::Traverse##CLASS)) { \ auto ILE = static_cast(S); \ if (auto Syn = ILE->isSemanticForm() ? ILE->getSyntacticForm() : ILE) \ TRY_TO(WalkUpFrom##CLASS(Syn)); \ if (auto Sem = ILE->isSemanticForm() ? ILE : ILE->getSemanticForm()) \ TRY_TO(WalkUpFrom##CLASS(Sem)); \ - break; \ - } + } \ + break; #include "clang/AST/StmtNodes.inc" } diff --git a/clang/unittests/Tooling/RecursiveASTVisitorTests/Callbacks.cpp b/clang/unittests/Tooling/RecursiveASTVisitorTests/Callbacks.cpp --- a/clang/unittests/Tooling/RecursiveASTVisitorTests/Callbacks.cpp +++ b/clang/unittests/Tooling/RecursiveASTVisitorTests/Callbacks.cpp @@ -117,18 +117,13 @@ Code, R"txt( TraverseIntegerLiteral IntegerLiteral(1) -WalkUpFromStmt IntegerLiteral(1) TraverseIntegerLiteral IntegerLiteral(2) -WalkUpFromStmt IntegerLiteral(2) TraverseIntegerLiteral IntegerLiteral(3) -WalkUpFromStmt IntegerLiteral(3) WalkUpFromStmt BinaryOperator(+) WalkUpFromStmt DeclRefExpr(add) WalkUpFromStmt ImplicitCastExpr TraverseIntegerLiteral IntegerLiteral(4) -WalkUpFromStmt IntegerLiteral(4) TraverseIntegerLiteral IntegerLiteral(5) -WalkUpFromStmt IntegerLiteral(5) WalkUpFromStmt CallExpr(add) WalkUpFromStmt CompoundStmt )txt")); @@ -189,18 +184,13 @@ Code, R"txt( TraverseIntegerLiteral IntegerLiteral(1) -WalkUpFromIntegerLiteral IntegerLiteral(1) TraverseIntegerLiteral IntegerLiteral(2) -WalkUpFromIntegerLiteral IntegerLiteral(2) TraverseIntegerLiteral IntegerLiteral(3) -WalkUpFromIntegerLiteral IntegerLiteral(3) WalkUpFromExpr BinaryOperator(+) WalkUpFromExpr DeclRefExpr(add) WalkUpFromExpr ImplicitCastExpr TraverseIntegerLiteral IntegerLiteral(4) -WalkUpFromIntegerLiteral IntegerLiteral(4) TraverseIntegerLiteral IntegerLiteral(5) -WalkUpFromIntegerLiteral IntegerLiteral(5) WalkUpFromExpr CallExpr(add) WalkUpFromStmt CompoundStmt )txt")); @@ -315,7 +305,6 @@ WalkUpFromStmt IntegerLiteral(1) WalkUpFromStmt IntegerLiteral(2) WalkUpFromStmt IntegerLiteral(3) -WalkUpFromStmt BinaryOperator(+) WalkUpFromStmt DeclRefExpr(add) WalkUpFromStmt ImplicitCastExpr WalkUpFromStmt IntegerLiteral(4) @@ -383,7 +372,6 @@ WalkUpFromExpr IntegerLiteral(1) WalkUpFromExpr IntegerLiteral(2) WalkUpFromExpr IntegerLiteral(3) -WalkUpFromBinaryOperator BinaryOperator(+) WalkUpFromExpr DeclRefExpr(add) WalkUpFromExpr ImplicitCastExpr WalkUpFromExpr IntegerLiteral(4) @@ -500,7 +488,6 @@ WalkUpFromStmt IntegerLiteral(3) WalkUpFromStmt BinaryOperator(+) TraverseCallExpr CallExpr(add) -WalkUpFromStmt CallExpr(add) WalkUpFromStmt CompoundStmt )txt")); } @@ -560,7 +547,6 @@ WalkUpFromExpr IntegerLiteral(3) WalkUpFromExpr BinaryOperator(+) TraverseCallExpr CallExpr(add) -WalkUpFromCallExpr CallExpr(add) WalkUpFromStmt CompoundStmt )txt")); }