forked from OSchip/llvm-project
Add cxxStdInitializerListExpr AST matcher
Summary: This adds a new ASTMatcher for CXXStdInitializerListExprs that matches C++ initializer list expressions. The primary motivation is to use it to fix [[ https://bugs.llvm.org/show_bug.cgi?id=32896 | PR32896 ]] (review here [[ https://reviews.llvm.org/D32767 | D32767 ]]). Reviewers: alexfh, Prazek, aaron.ballman Reviewed By: alexfh, aaron.ballman Subscribers: malcolm.parsons, cfe-commits, klimek Differential Revision: https://reviews.llvm.org/D32810 llvm-svn: 302287
This commit is contained in:
parent
430a335b7b
commit
64b6c78e94
|
@ -924,6 +924,19 @@ in
|
|||
</pre></td></tr>
|
||||
|
||||
|
||||
<tr><td>Matcher<<a href="http://clang.llvm.org/doxygen/classclang_1_1Stmt.html">Stmt</a>></td><td class="name" onclick="toggle('cxxStdInitializerListExpr0')"><a name="cxxStdInitializerListExpr0Anchor">cxxStdInitializerListExpr</a></td><td>Matcher<<a href="http://clang.llvm.org/doxygen/classclang_1_1CXXStdInitializerListExpr.html">CXXStdInitializerListExpr</a>>...</td></tr>
|
||||
<tr><td colspan="4" class="doc" id="cxxStdInitializerListExpr0"><pre>Matches C++ initializer list expressions.
|
||||
|
||||
Given
|
||||
std::vector<int> a({ 1, 2, 3 });
|
||||
std::vector<int> b = { 4, 5 };
|
||||
int c[] = { 6, 7 };
|
||||
std::pair<int, int> d = { 8, 9 };
|
||||
cxxStdInitializerListExpr()
|
||||
matches "{ 1, 2, 3 }" and "{ 4, 5 }"
|
||||
</pre></td></tr>
|
||||
|
||||
|
||||
<tr><td>Matcher<<a href="http://clang.llvm.org/doxygen/classclang_1_1Stmt.html">Stmt</a>></td><td class="name" onclick="toggle('cxxTemporaryObjectExpr0')"><a name="cxxTemporaryObjectExpr0Anchor">cxxTemporaryObjectExpr</a></td><td>Matcher<<a href="http://clang.llvm.org/doxygen/classclang_1_1CXXTemporaryObjectExpr.html">CXXTemporaryObjectExpr</a>>...</td></tr>
|
||||
<tr><td colspan="4" class="doc" id="cxxTemporaryObjectExpr0"><pre>Matches functional cast expressions having N != 1 arguments
|
||||
|
||||
|
@ -1160,7 +1173,7 @@ Example matches [&](){return 5;}
|
|||
<tr><td colspan="4" class="doc" id="materializeTemporaryExpr0"><pre>Matches nodes where temporaries are materialized.
|
||||
|
||||
Example: Given
|
||||
struct T {void func()};
|
||||
struct T {void func();};
|
||||
T f();
|
||||
void g(T);
|
||||
materializeTemporaryExpr() matches 'f()' in these statements
|
||||
|
@ -5233,7 +5246,7 @@ Example matches y in x(y)
|
|||
<tr><td colspan="4" class="doc" id="hasReceiverType0"><pre>Matches on the receiver of an ObjectiveC Message expression.
|
||||
|
||||
Example
|
||||
matcher = objCMessageExpr(hasRecieverType(asString("UIWebView *")));
|
||||
matcher = objCMessageExpr(hasReceiverType(asString("UIWebView *")));
|
||||
matches the [webView ...] message invocation.
|
||||
NSString *webViewJavaScript = ...
|
||||
UIWebView *webView = ...
|
||||
|
|
|
@ -1223,6 +1223,20 @@ AST_MATCHER_P(InitListExpr, hasSyntacticForm,
|
|||
InnerMatcher.matches(*SyntForm, Finder, Builder));
|
||||
}
|
||||
|
||||
/// \brief Matches C++ initializer list expressions.
|
||||
///
|
||||
/// Given
|
||||
/// \code
|
||||
/// std::vector<int> a({ 1, 2, 3 });
|
||||
/// std::vector<int> b = { 4, 5 };
|
||||
/// int c[] = { 6, 7 };
|
||||
/// std::pair<int, int> d = { 8, 9 };
|
||||
/// \endcode
|
||||
/// cxxStdInitializerListExpr()
|
||||
/// matches "{ 1, 2, 3 }" and "{ 4, 5 }"
|
||||
const internal::VariadicDynCastAllOfMatcher<Stmt,
|
||||
CXXStdInitializerListExpr> cxxStdInitializerListExpr;
|
||||
|
||||
/// \brief Matches implicit initializers of init list expressions.
|
||||
///
|
||||
/// Given
|
||||
|
|
|
@ -153,6 +153,7 @@ RegistryMaps::RegistryMaps() {
|
|||
REGISTER_MATCHER(cxxRecordDecl);
|
||||
REGISTER_MATCHER(cxxReinterpretCastExpr);
|
||||
REGISTER_MATCHER(cxxStaticCastExpr);
|
||||
REGISTER_MATCHER(cxxStdInitializerListExpr);
|
||||
REGISTER_MATCHER(cxxTemporaryObjectExpr);
|
||||
REGISTER_MATCHER(cxxThisExpr);
|
||||
REGISTER_MATCHER(cxxThrowExpr);
|
||||
|
|
|
@ -1020,6 +1020,29 @@ TEST(InitListExpression, MatchesInitListExpression) {
|
|||
matches("int i[1] = {42, [0] = 43};", integerLiteral(equals(42))));
|
||||
}
|
||||
|
||||
TEST(CXXStdInitializerListExpression, MatchesCXXStdInitializerListExpression) {
|
||||
const std::string code = "namespace std {"
|
||||
"template <typename> class initializer_list {"
|
||||
" public: initializer_list() noexcept {}"
|
||||
"};"
|
||||
"}"
|
||||
"struct A {"
|
||||
" A(std::initializer_list<int>) {}"
|
||||
"};";
|
||||
EXPECT_TRUE(matches(code + "A a{0};",
|
||||
cxxConstructExpr(has(cxxStdInitializerListExpr()),
|
||||
hasDeclaration(cxxConstructorDecl(
|
||||
ofClass(hasName("A")))))));
|
||||
EXPECT_TRUE(matches(code + "A a = {0};",
|
||||
cxxConstructExpr(has(cxxStdInitializerListExpr()),
|
||||
hasDeclaration(cxxConstructorDecl(
|
||||
ofClass(hasName("A")))))));
|
||||
|
||||
EXPECT_TRUE(notMatches("int a[] = { 1, 2 };", cxxStdInitializerListExpr()));
|
||||
EXPECT_TRUE(notMatches("struct B { int x, y; }; B b = { 5, 6 };",
|
||||
cxxStdInitializerListExpr()));
|
||||
}
|
||||
|
||||
TEST(UsingDeclaration, MatchesUsingDeclarations) {
|
||||
EXPECT_TRUE(matches("namespace X { int x; } using X::x;",
|
||||
usingDecl()));
|
||||
|
|
Loading…
Reference in New Issue