diff options
Diffstat (limited to 'clang-tools-extra/clang-tidy/bugprone/StringConstructorCheck.cpp')
-rw-r--r-- | clang-tools-extra/clang-tidy/bugprone/StringConstructorCheck.cpp | 16 |
1 files changed, 16 insertions, 0 deletions
diff --git a/clang-tools-extra/clang-tidy/bugprone/StringConstructorCheck.cpp b/clang-tools-extra/clang-tidy/bugprone/StringConstructorCheck.cpp index d88823067f2..cc6e2973a0c 100644 --- a/clang-tools-extra/clang-tidy/bugprone/StringConstructorCheck.cpp +++ b/clang-tools-extra/clang-tidy/bugprone/StringConstructorCheck.cpp @@ -100,6 +100,15 @@ void StringConstructorCheck::registerMatchers(MatchFinder *Finder) { integerLiteral().bind("int")))))) .bind("constructor"), this); + + // Check the literal string constructor with char pointer. + // [i.e. string (const char* s);] + Finder->addMatcher( + cxxConstructExpr(hasDeclaration(cxxMethodDecl(hasName("basic_string"))), + hasArgument(0, expr().bind("from-ptr")), + hasArgument(1, unless(hasType(isInteger())))) + .bind("constructor"), + this); } void StringConstructorCheck::check(const MatchFinder::MatchResult &Result) { @@ -128,6 +137,13 @@ void StringConstructorCheck::check(const MatchFinder::MatchResult &Result) { if (Lit->getValue().ugt(Str->getLength())) { diag(Loc, "length is bigger then string literal size"); } + } else if (const auto *Ptr = Result.Nodes.getNodeAs<Expr>("from-ptr")) { + Expr::EvalResult ConstPtr; + if (Ptr->EvaluateAsRValue(ConstPtr, Ctx) && + ((ConstPtr.Val.isInt() && ConstPtr.Val.getInt().isNullValue()) || + (ConstPtr.Val.isLValue() && ConstPtr.Val.isNullPointer()))) { + diag(Loc, "constructing string from nullptr is undefined behaviour"); + } } } |