using ::clang::transformer::node;
using ::clang::transformer::RewriteRule;
+AST_MATCHER(Type, isCharType) { return Node.isCharType(); }
+
static const char DefaultStringLikeClasses[] = "::std::basic_string;"
"::std::basic_string_view;"
"::absl::string_view";
hasUnqualifiedDesugaredType(recordType(hasDeclaration(StringLikeClass)));
auto CharStarType =
hasUnqualifiedDesugaredType(pointerType(pointee(isAnyCharacter())));
+ auto CharType = hasUnqualifiedDesugaredType(isCharType());
auto StringNpos = declRefExpr(
to(varDecl(hasName("npos"), hasDeclContext(StringLikeClass))));
auto StringFind = cxxMemberCallExpr(
callee(cxxMethodDecl(
hasName("find"),
- hasParameter(0, parmVarDecl(anyOf(hasType(StringType),
- hasType(CharStarType)))))),
+ hasParameter(
+ 0, parmVarDecl(anyOf(hasType(StringType), hasType(CharStarType),
+ hasType(CharType)))))),
on(hasType(StringType)), hasArgument(0, expr().bind("parameter_to_find")),
anyOf(hasArgument(1, integerLiteral(equals(0))),
hasArgument(1, cxxDefaultArgExpr())),
// CHECK-FIXES: {{^[[:space:]]*}}!absl::StrContains(asv, cc);{{$}}
}
-// Confirms that it does *not* match when the parameter to find() is a char,
-// because absl::StrContains is not implemented for char.
-void no_char_param_tests() {
+void char_param_tests() {
std::string ss;
ss.find('c') == std::string::npos;
+ // CHECK-MESSAGES: :[[@LINE-1]]:3: warning: use !absl::StrContains instead of
+ // CHECK-FIXES: {{^[[:space:]]*}}!absl::StrContains(ss, 'c');{{$}}
std::string_view ssv;
ssv.find('c') == std::string_view::npos;
+ // CHECK-MESSAGES: :[[@LINE-1]]:3: warning: use !absl::StrContains instead of
+ // CHECK-FIXES: {{^[[:space:]]*}}!absl::StrContains(ssv, 'c');{{$}}
absl::string_view asv;
asv.find('c') == absl::string_view::npos;
+ // CHECK-MESSAGES: :[[@LINE-1]]:3: warning: use !absl::StrContains instead of
+ // CHECK-FIXES: {{^[[:space:]]*}}!absl::StrContains(asv, 'c');{{$}}
}
#define FOO(a, b, c, d) ((a).find(b) == std::string::npos ? (c) : (d))