Index: include/clang/AST/ExprCXX.h =================================================================== --- include/clang/AST/ExprCXX.h +++ include/clang/AST/ExprCXX.h @@ -87,6 +87,8 @@ /// \brief Is this written as an infix binary operator? bool isInfixBinaryOp() const; + bool isPrefixOp() const; + /// \brief Returns the location of the operator symbol in the expression. /// /// When \c getOperator()==OO_Call, this is the location of the right Index: include/clang/AST/LexicallyOrderedRecursiveASTVisitor.h =================================================================== --- include/clang/AST/LexicallyOrderedRecursiveASTVisitor.h +++ include/clang/AST/LexicallyOrderedRecursiveASTVisitor.h @@ -111,33 +111,6 @@ return true; } - Stmt::child_range getStmtChildren(Stmt *S) { return S->children(); } - - SmallVector getStmtChildren(CXXOperatorCallExpr *CE) { - SmallVector Children(CE->children()); - bool Swap; - // Switch the operator and the first operand for all infix and postfix - // operations. - switch (CE->getOperator()) { - case OO_Arrow: - case OO_Call: - case OO_Subscript: - Swap = true; - break; - case OO_PlusPlus: - case OO_MinusMinus: - // These are postfix unless there is exactly one argument. - Swap = Children.size() != 2; - break; - default: - Swap = CE->isInfixBinaryOp(); - break; - } - if (Swap && Children.size() > 1) - std::swap(Children[0], Children[1]); - return Children; - } - private: bool TraverseAdditionalLexicallyNestedDeclarations() { // FIXME: Ideally the gathered declarations and the declarations in the Index: include/clang/AST/RecursiveASTVisitor.h =================================================================== --- include/clang/AST/RecursiveASTVisitor.h +++ include/clang/AST/RecursiveASTVisitor.h @@ -315,8 +315,6 @@ // ---- Methods on Stmts ---- - Stmt::child_range getStmtChildren(Stmt *S) { return S->children(); } - private: template struct has_same_member_pointer_type : std::false_type {}; @@ -2080,15 +2078,26 @@ TRY_TO(WalkUpFrom##STMT(S)); \ { CODE; } \ if (ShouldVisitChildren) { \ - for (Stmt * SubStmt : getDerived().getStmtChildren(S)) { \ - TRY_TO_TRAVERSE_OR_ENQUEUE_STMT(SubStmt); \ + auto ChildIterator = S->child_begin(); \ + /* Make the operator come second for infix and postfix overloaded \ + * operators. */ \ + if (auto *CE = dyn_cast(S)) { \ + if (CE->isInfixBinaryOp() || !CE->isPrefixOp()) { \ + Stmt *Operator = *ChildIterator; \ + TRY_TO_TRAVERSE_OR_ENQUEUE_STMT(*++ChildIterator); \ + TRY_TO_TRAVERSE_OR_ENQUEUE_STMT(Operator); \ + ++ChildIterator; \ + } \ + } \ + for (auto ChildEnd = S->child_end(); ChildIterator != ChildEnd; \ + ++ChildIterator) { \ + TRY_TO_TRAVERSE_OR_ENQUEUE_STMT(*ChildIterator); \ } \ } \ if (!Queue && ReturnValue && getDerived().shouldTraversePostOrder()) \ TRY_TO(WalkUpFrom##STMT(S)); \ return ReturnValue; \ } - DEF_TRAVERSE_STMT(GCCAsmStmt, { TRY_TO_TRAVERSE_OR_ENQUEUE_STMT(S->getAsmString()); for (unsigned I = 0, E = S->getNumInputs(); I < E; ++I) { Index: lib/AST/ExprCXX.cpp =================================================================== --- lib/AST/ExprCXX.cpp +++ lib/AST/ExprCXX.cpp @@ -41,6 +41,12 @@ } } +bool CXXOperatorCallExpr::isPrefixOp() const { + return getNumArgs() == 1 && getOperator() != OO_Call && + getOperator() != OO_Arrow; +} + + bool CXXTypeidExpr::isPotentiallyEvaluated() const { if (isTypeOperand()) return false;