================ @@ -1948,31 +2294,59 @@ class DerefSimplePtrArithFixableGadget : public FixableGadget { const IntegerLiteral *Offset = nullptr; public: - DerefSimplePtrArithFixableGadget(const MatchFinder::MatchResult &Result) + DerefSimplePtrArithFixableGadget(const MatchResult &Result) : FixableGadget(Kind::DerefSimplePtrArithFixable), - BaseDeclRefExpr( - Result.Nodes.getNodeAs<DeclRefExpr>(BaseDeclRefExprTag)), - DerefOp(Result.Nodes.getNodeAs<UnaryOperator>(DerefOpTag)), - AddOp(Result.Nodes.getNodeAs<BinaryOperator>(AddOpTag)), - Offset(Result.Nodes.getNodeAs<IntegerLiteral>(OffsetTag)) {} - - static Matcher matcher() { - // clang-format off - auto ThePtr = expr(hasPointerType(), - ignoringImpCasts(declRefExpr(toSupportedVariable()). - bind(BaseDeclRefExprTag))); - auto PlusOverPtrAndInteger = expr(anyOf( - binaryOperator(hasOperatorName("+"), hasLHS(ThePtr), - hasRHS(integerLiteral().bind(OffsetTag))) - .bind(AddOpTag), - binaryOperator(hasOperatorName("+"), hasRHS(ThePtr), - hasLHS(integerLiteral().bind(OffsetTag))) - .bind(AddOpTag))); - return isInUnspecifiedLvalueContext(unaryOperator( - hasOperatorName("*"), - hasUnaryOperand(ignoringParens(PlusOverPtrAndInteger))) - .bind(DerefOpTag)); - // clang-format on + BaseDeclRefExpr(Result.getNodeAs<DeclRefExpr>(BaseDeclRefExprTag)), + DerefOp(Result.getNodeAs<UnaryOperator>(DerefOpTag)), + AddOp(Result.getNodeAs<BinaryOperator>(AddOpTag)), + Offset(Result.getNodeAs<IntegerLiteral>(OffsetTag)) {} + + static bool matches(const Stmt *S, llvm::SmallVector<MatchResult> &Results) { + bool Found = false; + auto IsPtr = [](const Expr *E, MatchResult &R) { + if (!E || !hasPointerType(*E)) + return false; + const auto *DRE = dyn_cast<DeclRefExpr>(E->IgnoreImpCasts()); + if (!DRE || !isSupportedVariable(*DRE)) + return false; + R.addNode(BaseDeclRefExprTag, DynTypedNode::create(*DRE)); + return true; + }; + const auto PlusOverPtrAndInteger = [&IsPtr](const Expr *E, MatchResult &R) { + const auto *BO = dyn_cast<BinaryOperator>(E); + if (!BO || BO->getOpcode() != BO_Add) + return false; + + const auto *LHS = BO->getLHS(); + const auto *RHS = BO->getRHS(); + if (isa<IntegerLiteral>(RHS) && IsPtr(LHS, R)) { + R.addNode(OffsetTag, DynTypedNode::create(*RHS)); + R.addNode(AddOpTag, DynTypedNode::create(*BO)); + return true; + } + if (isa<IntegerLiteral>(LHS) && IsPtr(RHS, R)) { + R.addNode(OffsetTag, DynTypedNode::create(*LHS)); + R.addNode(AddOpTag, DynTypedNode::create(*BO)); + return true; + } + return false; + }; + const auto InnerMatcher = [&PlusOverPtrAndInteger, &Found, + &Results](const Expr *E) { + const auto *UO = dyn_cast<UnaryOperator>(E); + if (!UO || UO->getOpcode() != UO_Deref) + return; + + const auto *Operand = UO->getSubExpr()->IgnoreParens(); + MatchResult R; + if (PlusOverPtrAndInteger(Operand, R)) { + R.addNode(DerefOpTag, DynTypedNode::create(*UO)); + Results.emplace_back(R); ---------------- ilya-biryukov wrote:
NIT: std::move(R) for efficiency. https://github.com/llvm/llvm-project/pull/125492 _______________________________________________ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits