diff --git a/clang/docs/LibASTMatchersReference.html b/clang/docs/LibASTMatchersReference.html --- a/clang/docs/LibASTMatchersReference.html +++ b/clang/docs/LibASTMatchersReference.html @@ -996,6 +996,17 @@ +Matcher<Decl>objcTypeParamDeclMatcher<ObjCTypeParamDecl>... +
Matches the declaration of an Objective-C type parameter.
+
+Given
+  @interface C <X: id>
+  @end
+objcTypeParamDecl()
+  matches the type-parameter declaration "X".
+
+ + Matcher<Decl>parmVarDeclMatcher<ParmVarDecl>...
Matches parameter variable declarations.
 
@@ -2439,6 +2450,16 @@
 
+Matcher<Type>bitIntTypeMatcher<BitIntType>... +
Matches a fixed int type of a specified bit width.
+
+Given:
+  _BitInt(10) i;
+bitIntType()
+  matches "_BitInt(10) i".
+
+ + Matcher<Type>blockPointerTypeMatcher<BlockPointerType>...
Matches block pointer types, i.e. types syntactically represented as
 "void (^)(int)".
@@ -2485,6 +2506,16 @@
 
+Matcher<Type>constantMatrixTypeMatcher<ConstantMatrixType>... +
Matches matrix types of constant size.
+
+Given:
+  typedef int __attribute__((matrix_type(5, 5))) X;
+constantMatrixType()
+  matches the type of the typedef declaration "X".
+
+ + Matcher<Type>decayedTypeMatcher<DecayedType>...
Matches decayed type
 Example matches i[] in declaration of f.
@@ -2523,6 +2554,30 @@
 
+Matcher<Type>dependentAddressSpaceTypeMatcher<DependentAddressSpaceType>... +
Matches an extended address space qualifier where the
+input address space value is dependent.
+
+Given
+  template<typename T, int AddrSpace>
+  class AddressSpace {
+    typedef T __attribute__((address_space(AddrSpace))) X;
+  };
+dependentAddressSpaceType()
+  matches the type of the typedef declaration "X".
+
+ + +Matcher<Type>dependentBitIntTypeMatcher<DependentBitIntType>... +
Matches a fixed int type where the bit width is dependent.
+
+Given
+  template using X = _BitInt(Width);
+dependentBitIntType()
+  matches the type of the type alias declaration "X".
+
+ + Matcher<Type>dependentSizedArrayTypeMatcher<DependentSizedArrayType>...
Matches C++ arrays whose size is a value-dependent expression.
 
@@ -2549,6 +2604,35 @@
 
+Matcher<Type>dependentSizedMatrixTypeMatcher<DependentSizedMatrixType>... +
Matches a matrix type where the type and the number of rows
+and columns is dependent.
+
+Given
+  template<typename T, int Rows, int Cols>
+  class matrix {
+    typedef T __attribute__((matrix_type(Rows, Cols))) X;
+  };
+  typedef int __attribute__((matrix_type(3, 3))) Y;
+dependentSizedMatrixType()
+  matches the type of the typedef declaration "X" but not "Y".
+
+ + +Matcher<Type>dependentVectorTypeMatcher<DependentVectorType>... +
Matches vector types where either the type or size is dependent.
+
+Given
+  template<typename T, int Size>
+  class vector {
+    typedef T __attribute__((vector_size(Size))) X;
+  };
+  typedef int __attribute__((vector_size(12))) Y;
+dependentVectorType()
+  matches the type of the typedef declaration "X" but not "Y".
+
+ + Matcher<Type>elaboratedTypeMatcher<ElaboratedType>...
Matches types specified with an elaborated type keyword or with a
 qualified name.
@@ -2680,11 +2764,22 @@
   @interface Foo
   @end
   Foo *f;
-pointerType()
+objcObjectPointerType()
   matches "Foo *f", but does not match "int *a".
 
+Matcher<Type>objcTypeParamTypeMatcher<ObjCTypeParamType>... +
Matches Objective-C type parameter types.
+
+Given
+  @interface C <X: id>
+  @end
+objcTypeParamType()
+  matches the type of type-parameter "X".
+
+ + Matcher<Type>parenTypeMatcher<ParenType>...
Matches ParenType nodes.
 
@@ -2697,6 +2792,17 @@
 
+Matcher<Type>pipeTypeMatcher<PipeType>... +
Matches OpenCL pipe types.
+
+Given
+  typedef pipe int X;
+  typedef int Y;
+pipeType()
+  matches the type of the typedef declaration "X" but not "Y".
+
+ + Matcher<Type>pointerTypeMatcher<PointerType>...
Matches pointer types, but does not match Objective-C object pointer
 types.
@@ -2866,6 +2972,16 @@
   matches "int c[a[0]]"
 
+ +Matcher<Type>vectorTypeMatcher<VectorType>... +
Matches vector types.
+
+Given
+  typedef int __attribute__((vector_size(12))) X;
+vectorType()
+  matches the type of the typedef declaration "X".
+
+ @@ -9918,6 +10034,11 @@ +Matcher<TypeDecl>hasTypeForDeclMatcher<QualType> InnerMatcher +
Matches the type object that represents this TypeDecl.
+
+ + Matcher<TypedefNameDecl>hasTypeLocMatcher<TypeLoc> Inner
Matches if the type location of a node matches the inner matcher.
 
diff --git a/clang/docs/ReleaseNotes.rst b/clang/docs/ReleaseNotes.rst
--- a/clang/docs/ReleaseNotes.rst
+++ b/clang/docs/ReleaseNotes.rst
@@ -293,9 +293,20 @@
 
 AST Matchers
 ------------
+- Add ``bitIntType``.
+- Add ``constantMatrixType``.
 - Add ``convertVectorExpr``.
+- Add ``dependentAddressSpaceType``.
+- Add ``dependentBitIntType``.
 - Add ``dependentSizedExtVectorType``.
+- Add ``dependentSizedMatrixType``.
+- Add ``dependentVectorType``.
 - Add ``macroQualifiedType``.
+- Add ``hasTypeForDecl``.
+- Add ``objcTypeParamDecl``.
+- Add ``objcTypeParamType``.
+- Add ``pipeType``.
+- Add ``vectorType``.
 
 clang-format
 ------------
diff --git a/clang/include/clang/ASTMatchers/ASTMatchers.h b/clang/include/clang/ASTMatchers/ASTMatchers.h
--- a/clang/include/clang/ASTMatchers/ASTMatchers.h
+++ b/clang/include/clang/ASTMatchers/ASTMatchers.h
@@ -3968,6 +3968,15 @@
   return false;
 }
 
+/// Matches the type object that represents this TypeDecl.
+AST_MATCHER_P(TypeDecl, hasTypeForDecl, internal::Matcher,
+              InnerMatcher) {
+  QualType QT(Node.getTypeForDecl(), 0);
+  if (!QT.isNull())
+    return InnerMatcher.matches(QT, Finder, Builder);
+  return false;
+}
+
 /// Overloaded to match the declaration of the expression's or value
 /// declaration's type.
 ///
@@ -7049,6 +7058,124 @@
 ///   matches "decltype(i + j)"
 extern const AstTypeMatcher decltypeType;
 
+/// Matches a fixed int type of a specified bit width.
+///
+/// Given
+/// \code
+///   _BitInt(10) i;
+/// \endcode
+/// bitIntType()
+///   matches "_BitInt(10) i"
+extern const AstTypeMatcher bitIntType;
+
+/// Matches matrix types of constant size.
+///
+/// Given
+/// \code
+///   typedef int __attribute__((matrix_type(5, 5))) X;
+/// \endcode
+/// constantMatrixType()
+///   matches the type of the typedef declaration "X".
+extern const AstTypeMatcher constantMatrixType;
+
+/// Matches an extended address space qualifier where the input address space
+/// value is dependent.
+///
+/// Given
+/// \code
+///   template
+///   class AddressSpace {
+///     typedef T __attribute__((address_space(AddrSpace))) X;
+///   };
+/// \endcode
+/// dependentAddressSpaceType()
+///   matches the type of the typedef declaration "X".
+extern const AstTypeMatcher
+    dependentAddressSpaceType;
+
+/// Matches a fixed int type where the bit width is dependent.
+///
+/// Given
+/// \code
+///   template using X = _BitInt(Width);
+/// \endcode
+/// dependentBitIntType()
+///   matches the type of the type alias declaration "X".
+extern const AstTypeMatcher dependentBitIntType;
+
+/// Matches vector types where either the type or size is dependent.
+///
+/// Given
+/// \code
+///   template
+///   class vector {
+///     typedef T __attribute__((vector_size(Size))) X;
+///   };
+///   typedef int __attribute__((vector_size(12))) Y;
+/// \endcode
+/// dependentVectorType()
+///   matches the type of the typedef declaration "X" but not "Y".
+extern const AstTypeMatcher dependentVectorType;
+
+/// Matches a matrix type where the type and the number of rows and columns
+/// is dependent.
+///
+/// Given
+/// \code
+///   template
+///   class matrix {
+///     typedef T __attribute__((matrix_type(Rows, Cols))) X;
+///   };
+///   typedef int __attribute__((matrix_type(3, 3))) Y;
+/// \endcode
+/// dependentSizedMatrixType()
+///   matches the type of the typedef declaration "X" but not "Y".
+extern const AstTypeMatcher dependentSizedMatrixType;
+
+/// Matches vector types.
+///
+/// Given
+/// \code
+///   typedef int __attribute__((vector_size(12))) X;
+/// \endcode
+/// vectorType()
+///   matches the type of the typedef declaration "X".
+extern const AstTypeMatcher vectorType;
+
+/// Matches Objective-C type parameter types.
+///
+/// Given
+/// \code
+///   @interface C 
+///   @end
+/// \endcode
+/// objcTypeParamType()
+///   matches the type of type-parameter "X".
+extern const AstTypeMatcher objcTypeParamType;
+
+/// Matches the declaration of an Objective-C type parameter.
+///
+/// Given
+/// \code
+///   @interface C 
+///   @end
+/// \endcode
+/// objcTypeParamDecl()
+///   matches the type-parameter declaration "X".
+extern const internal::VariadicDynCastAllOfMatcher
+    objcTypeParamDecl;
+
+/// Matches OpenCL pipe types.
+///
+/// Given
+/// \code
+///   typedef pipe int X;
+///   typedef int Y;
+/// \endcode
+/// pipeType()
+///   matches the type of the typedef declaration \c X but not \c Y.
+extern const AstTypeMatcher pipeType;
+
 /// Matches \c AutoType nodes where the deduced type is a specific type.
 ///
 /// Note: There is no \c TypeLoc for the deduced type and thus no
diff --git a/clang/lib/ASTMatchers/ASTMatchFinder.cpp b/clang/lib/ASTMatchers/ASTMatchFinder.cpp
--- a/clang/lib/ASTMatchers/ASTMatchFinder.cpp
+++ b/clang/lib/ASTMatchers/ASTMatchFinder.cpp
@@ -504,6 +504,7 @@
   bool TraverseNestedNameSpecifierLoc(NestedNameSpecifierLoc NNS);
   bool TraverseConstructorInitializer(CXXCtorInitializer *CtorInit);
   bool TraverseTemplateArgumentLoc(TemplateArgumentLoc TAL);
+  bool TraverseObjCTypeParamDecl(ObjCTypeParamDecl *TPD);
   bool TraverseAttr(Attr *AttrNode);
 
   bool dataTraverseNode(Stmt *S, DataRecursionQueue *Queue) {
@@ -1521,6 +1522,11 @@
   return RecursiveASTVisitor::TraverseTemplateArgumentLoc(Loc);
 }
 
+bool MatchASTVisitor::TraverseObjCTypeParamDecl(ObjCTypeParamDecl *TPD) {
+  match(*TPD);
+  return RecursiveASTVisitor::TraverseObjCTypeParamDecl(TPD);
+}
+
 bool MatchASTVisitor::TraverseAttr(Attr *AttrNode) {
   match(*AttrNode);
   return RecursiveASTVisitor::TraverseAttr(AttrNode);
diff --git a/clang/lib/ASTMatchers/ASTMatchersInternal.cpp b/clang/lib/ASTMatchers/ASTMatchersInternal.cpp
--- a/clang/lib/ASTMatchers/ASTMatchersInternal.cpp
+++ b/clang/lib/ASTMatchers/ASTMatchersInternal.cpp
@@ -839,6 +839,8 @@
 const internal::VariadicDynCastAllOfMatcher objcIvarDecl;
 const internal::VariadicDynCastAllOfMatcher
     objcPropertyDecl;
+const internal::VariadicDynCastAllOfMatcher
+    objcTypeParamDecl;
 const internal::VariadicDynCastAllOfMatcher
     objcThrowStmt;
 const internal::VariadicDynCastAllOfMatcher objcTryStmt;
@@ -1049,6 +1051,15 @@
     deducedTemplateSpecializationType;
 const AstTypeMatcher dependentSizedArrayType;
 const AstTypeMatcher dependentSizedExtVectorType;
+const AstTypeMatcher bitIntType;
+const AstTypeMatcher dependentBitIntType;
+const AstTypeMatcher dependentAddressSpaceType;
+const AstTypeMatcher constantMatrixType;
+const AstTypeMatcher dependentSizedMatrixType;
+const AstTypeMatcher dependentVectorType;
+const AstTypeMatcher vectorType;
+const AstTypeMatcher pipeType;
+const AstTypeMatcher objcTypeParamType;
 const AstTypeMatcher incompleteArrayType;
 const AstTypeMatcher variableArrayType;
 const AstTypeMatcher atomicType;
diff --git a/clang/lib/ASTMatchers/Dynamic/Registry.cpp b/clang/lib/ASTMatchers/Dynamic/Registry.cpp
--- a/clang/lib/ASTMatchers/Dynamic/Registry.cpp
+++ b/clang/lib/ASTMatchers/Dynamic/Registry.cpp
@@ -151,6 +151,7 @@
   REGISTER_MATCHER(binaryOperator);
   REGISTER_MATCHER(binaryOperation);
   REGISTER_MATCHER(bindingDecl);
+  REGISTER_MATCHER(bitIntType);
   REGISTER_MATCHER(blockDecl);
   REGISTER_MATCHER(blockExpr);
   REGISTER_MATCHER(blockPointerType);
@@ -176,6 +177,7 @@
   REGISTER_MATCHER(conditionalOperator);
   REGISTER_MATCHER(constantArrayType);
   REGISTER_MATCHER(constantExpr);
+  REGISTER_MATCHER(constantMatrixType);
   REGISTER_MATCHER(containsDeclaration);
   REGISTER_MATCHER(continueStmt);
   REGISTER_MATCHER(convertVectorExpr);
@@ -226,9 +228,13 @@
   REGISTER_MATCHER(decltypeType);
   REGISTER_MATCHER(deducedTemplateSpecializationType);
   REGISTER_MATCHER(defaultStmt);
+  REGISTER_MATCHER(dependentAddressSpaceType);
+  REGISTER_MATCHER(dependentBitIntType);
   REGISTER_MATCHER(dependentCoawaitExpr);
   REGISTER_MATCHER(dependentSizedArrayType);
   REGISTER_MATCHER(dependentSizedExtVectorType);
+  REGISTER_MATCHER(dependentSizedMatrixType);
+  REGISTER_MATCHER(dependentVectorType);
   REGISTER_MATCHER(designatedInitExpr);
   REGISTER_MATCHER(designatorCountIs);
   REGISTER_MATCHER(doStmt);
@@ -371,6 +377,7 @@
   REGISTER_MATCHER(hasThreadStorageDuration);
   REGISTER_MATCHER(hasTrailingReturn);
   REGISTER_MATCHER(hasTrueExpression);
+  REGISTER_MATCHER(hasTypeForDecl);
   REGISTER_MATCHER(hasTypeLoc);
   REGISTER_MATCHER(hasUnaryOperand);
   REGISTER_MATCHER(hasUnarySelector);
@@ -517,6 +524,8 @@
   REGISTER_MATCHER(objcStringLiteral);
   REGISTER_MATCHER(objcThrowStmt);
   REGISTER_MATCHER(objcTryStmt);
+  REGISTER_MATCHER(objcTypeParamDecl);
+  REGISTER_MATCHER(objcTypeParamType);
   REGISTER_MATCHER(ofClass);
   REGISTER_MATCHER(ofKind);
   REGISTER_MATCHER(ompDefaultClause);
@@ -530,6 +539,7 @@
   REGISTER_MATCHER(parenListExpr);
   REGISTER_MATCHER(parenType);
   REGISTER_MATCHER(parmVarDecl);
+  REGISTER_MATCHER(pipeType);
   REGISTER_MATCHER(pointee);
   REGISTER_MATCHER(pointerType);
   REGISTER_MATCHER(pointerTypeLoc);
@@ -599,6 +609,7 @@
   REGISTER_MATCHER(valueDecl);
   REGISTER_MATCHER(varDecl);
   REGISTER_MATCHER(variableArrayType);
+  REGISTER_MATCHER(vectorType);
   REGISTER_MATCHER(voidType);
   REGISTER_MATCHER(whileStmt);
   REGISTER_MATCHER(withInitializer);
diff --git a/clang/unittests/ASTMatchers/ASTMatchersNodeTest.cpp b/clang/unittests/ASTMatchers/ASTMatchersNodeTest.cpp
--- a/clang/unittests/ASTMatchers/ASTMatchersNodeTest.cpp
+++ b/clang/unittests/ASTMatchers/ASTMatchersNodeTest.cpp
@@ -1549,6 +1549,89 @@
   EXPECT_TRUE(matches("struct S {};", qualType().bind("loc")));
 }
 
+TEST_P(ASTMatchersTest, BitIntType) {
+  StringRef code = "_BitInt(10) i;";
+  EXPECT_TRUE(matches(code, varDecl(hasType(bitIntType()))));
+  EXPECT_TRUE(notMatches(code, varDecl(hasType(builtinType()))));
+}
+
+TEST_P(ASTMatchersTest, ConstantMatrixType) {
+  StringRef Code = "typedef int __attribute__((matrix_type(5, 5))) X;";
+
+  EXPECT_TRUE(matchesWithMatrixEnabled(
+      Code, typedefDecl(hasType(constantMatrixType()))));
+  EXPECT_TRUE(
+      notMatchesWithMatrixEnabled(Code, typedefDecl(hasType(vectorType()))));
+}
+
+TEST_P(ASTMatchersTest, DependentAddressSpaceType) {
+  if (!GetParam().isCXX())
+    return;
+
+  StringRef Code = "template"
+                   "class vector {"
+                   "  typedef T __attribute__((address_space(AddrSpace))) X;"
+                   "};";
+  EXPECT_TRUE(matches(Code, typedefDecl(hasType(dependentAddressSpaceType()))));
+
+  EXPECT_TRUE(notMatches("int __attribute__((address_space(0))) X;",
+                         typedefDecl(hasType(dependentAddressSpaceType()))));
+}
+
+TEST_P(ASTMatchersTest, DependentBitIntType) {
+  if (!GetParam().isCXX11OrLater())
+    return;
+
+  EXPECT_TRUE(matches("template using X = _BitInt(Width);",
+                      typeAliasDecl(hasType(dependentBitIntType()))));
+
+  EXPECT_TRUE(notMatches("typedef _BitInt(10) Int10;",
+                         typedefDecl(hasType(dependentBitIntType()))));
+}
+
+TEST_P(ASTMatchersTest, DependentVectorType) {
+  if (!GetParam().isCXX())
+    return;
+
+  StringRef DepCode = "template"
+                      "class vector {"
+                      "  typedef T __attribute__((vector_size(Size))) X;"
+                      "};";
+  EXPECT_TRUE(matches(DepCode, dependentVectorType()));
+
+  StringRef NonDepCode = "typedef int __attribute__((vector_size(16))) X;";
+  EXPECT_TRUE(notMatches(NonDepCode, dependentVectorType()));
+}
+
+TEST_P(ASTMatchersTest, VectorType) {
+  if (!GetParam().isCXX())
+    return;
+
+  StringRef NonDepCode = "typedef int __attribute__((vector_size(16))) X;";
+  EXPECT_TRUE(matches(NonDepCode, vectorType()));
+
+  StringRef DepCode = "template"
+                      "class vector {"
+                      "  typedef T __attribute__((vector_size(Size))) X;"
+                      "};";
+  EXPECT_TRUE(notMatches(DepCode, vectorType()));
+}
+
+TEST_P(ASTMatchersTest, DependentSizedMatrixType) {
+  if (!GetParam().isCXX())
+    return;
+
+  StringRef DepCode = "template"
+                      "class matrix {"
+                      "  typedef T __attribute__((matrix_type(Rows, Cols))) X;"
+                      "};";
+  EXPECT_TRUE(matchesWithMatrixEnabled(DepCode, dependentSizedMatrixType()));
+
+  StringRef NonDepCode = "typedef int __attribute__((matrix_type(3, 3))) Y;";
+  EXPECT_TRUE(
+      notMatchesWithMatrixEnabled(NonDepCode, dependentSizedMatrixType()));
+}
+
 TEST_P(ASTMatchersTest, ConstantArrayType) {
   EXPECT_TRUE(matches("int a[2];", constantArrayType()));
   EXPECT_TRUE(notMatches("void f() { int a[] = { 2, 3 }; int b[a[0]]; }",
@@ -2518,6 +2601,28 @@
   EXPECT_TRUE(matchesObjC(ObjCString, objcFinallyStmt()));
 }
 
+TEST(ASTMatchersTestObjC, ObjCTypeParamDecl) {
+  StringRef ObjCString = "@interface C "
+                         "@end";
+  EXPECT_TRUE(matchesObjC(ObjCString, objcTypeParamDecl()));
+  EXPECT_TRUE(notMatchesObjC(ObjCString, parmVarDecl()));
+}
+
+TEST(ASTMatchersTestObjC, ObjCTypeParamType) {
+  StringRef ObjCString = "@interface C "
+                         "@end";
+  EXPECT_TRUE(matchesObjC(
+      ObjCString, objcTypeParamDecl(hasTypeForDecl(objcTypeParamType()))));
+  EXPECT_TRUE(notMatchesObjC(ObjCString,
+                             objcTypeParamDecl(hasTypeForDecl(builtinType()))));
+}
+
+TEST(ASTMatchersTestOpenCL, PipeType) {
+  StringRef code = "typedef pipe int X;";
+  EXPECT_TRUE(matchesOpenCL(code, typedefDecl(hasType(pipeType()))));
+  EXPECT_TRUE(notMatchesOpenCL(code, typedefDecl(hasType(isInteger()))));
+}
+
 TEST(ASTMatchersTest, DecompositionDecl) {
   StringRef Code = R"cpp(
 void foo()
diff --git a/clang/unittests/ASTMatchers/ASTMatchersTest.h b/clang/unittests/ASTMatchers/ASTMatchersTest.h
--- a/clang/unittests/ASTMatchers/ASTMatchersTest.h
+++ b/clang/unittests/ASTMatchers/ASTMatchersTest.h
@@ -284,6 +284,33 @@
                               {"-fopenmp=libomp", "-fopenmp-version=51"});
 }
 
+template 
+testing::AssertionResult matchesOpenCL(const Twine &Code, const T &AMatcher) {
+  return matchesConditionally(Code, AMatcher, true,
+                              {"-x", "cl", "-cl-no-stdinc", "-cl-std=CL2.0"},
+                              FileContentMappings(), "input.cl");
+}
+
+template 
+testing::AssertionResult notMatchesOpenCL(const Twine &Code,
+                                          const T &AMatcher) {
+  return matchesConditionally(Code, AMatcher, false,
+                              {"-x", "cl", "-cl-no-stdinc", "-cl-std=CL2.0"},
+                              FileContentMappings(), "input.cl");
+}
+
+template 
+testing::AssertionResult matchesWithMatrixEnabled(const Twine &Code,
+                                                  const T &AMatcher) {
+  return matchesConditionally(Code, AMatcher, true, {"-fenable-matrix"});
+}
+
+template 
+testing::AssertionResult notMatchesWithMatrixEnabled(const Twine &Code,
+                                                     const T &AMatcher) {
+  return matchesConditionally(Code, AMatcher, false, {"-fenable-matrix"});
+}
+
 template 
 testing::AssertionResult matchAndVerifyResultConditionally(
     const Twine &Code, const T &AMatcher,