11 #include "clang/AST/ASTContext.h" 12 #include "clang/ASTMatchers/ASTMatchFinder.h" 18 namespace cppcoreguidelines {
20 const internal::VariadicDynCastAllOfMatcher<Stmt, VAArgExpr>
vAArgExpr;
22 void ProTypeVarargCheck::registerMatchers(MatchFinder *Finder) {
23 if (!getLangOpts().CPlusPlus)
26 Finder->addMatcher(
vAArgExpr().bind(
"va_use"),
this);
29 callExpr(callee(functionDecl(isVariadic()))).bind(
"callvararg"),
this);
33 const auto *FDecl = dyn_cast<FunctionDecl>(C->getCalleeDecl());
37 auto N = FDecl->getNumParams();
38 if (C->getNumArgs() != N + 1)
42 dyn_cast<IntegerLiteral>(C->getArg(N)->IgnoreParenImpCasts());
46 if (IntLit->getValue() != I)
52 void ProTypeVarargCheck::check(
const MatchFinder::MatchResult &
Result) {
53 if (
const auto *Matched = Result.Nodes.getNodeAs<CallExpr>(
"callvararg")) {
56 diag(Matched->getExprLoc(),
"do not call c-style vararg functions");
59 if (
const auto *Matched = Result.Nodes.getNodeAs<Expr>(
"va_use")) {
60 diag(Matched->getExprLoc(),
61 "do not use va_start/va_arg to define c-style vararg functions; " 62 "use variadic templates instead");
65 if (
const auto *Matched = Result.Nodes.getNodeAs<VarDecl>(
"va_list")) {
66 auto SR = Matched->getSourceRange();
69 diag(SR.getBegin(),
"do not declare variables of type va_list; " 70 "use variadic templates instead");
const internal::VariadicDynCastAllOfMatcher< Stmt, VAArgExpr > vAArgExpr
llvm::Optional< llvm::Expected< tooling::AtomicChanges > > Result
===– Representation.cpp - ClangDoc Representation --------—*- C++ -*-===//
static bool hasSingleVariadicArgumentWithValue(const CallExpr *C, uint64_t I)