aboutsummaryrefslogtreecommitdiff
path: root/tools/libclang/CXCursor.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'tools/libclang/CXCursor.cpp')
-rw-r--r--tools/libclang/CXCursor.cpp167
1 files changed, 165 insertions, 2 deletions
diff --git a/tools/libclang/CXCursor.cpp b/tools/libclang/CXCursor.cpp
index 432190390b7f..7834181d4781 100644
--- a/tools/libclang/CXCursor.cpp
+++ b/tools/libclang/CXCursor.cpp
@@ -57,6 +57,7 @@ static CXCursorKind GetCursorKind(const Attr *A) {
case attr::CUDADevice: return CXCursor_CUDADeviceAttr;
case attr::CUDAGlobal: return CXCursor_CUDAGlobalAttr;
case attr::CUDAHost: return CXCursor_CUDAHostAttr;
+ case attr::CUDAShared: return CXCursor_CUDASharedAttr;
}
return CXCursor_UnexposedAttr;
@@ -228,6 +229,7 @@ CXCursor cxcursor::MakeCXCursor(const Stmt *S, const Decl *Parent,
case Stmt::CXXBindTemporaryExprClass:
case Stmt::CXXDefaultArgExprClass:
case Stmt::CXXDefaultInitExprClass:
+ case Stmt::CXXFoldExprClass:
case Stmt::CXXStdInitializerListExprClass:
case Stmt::CXXScalarValueInitExprClass:
case Stmt::CXXUuidofExprClass:
@@ -468,6 +470,7 @@ CXCursor cxcursor::MakeCXCursor(const Stmt *S, const Decl *Parent,
case Stmt::SubstNonTypeTemplateParmPackExprClass:
case Stmt::FunctionParmPackExprClass:
case Stmt::UnresolvedLookupExprClass:
+ case Stmt::TypoExprClass: // A typo could actually be a DeclRef or a MemberRef
K = CXCursor_DeclRefExpr;
break;
@@ -526,6 +529,9 @@ CXCursor cxcursor::MakeCXCursor(const Stmt *S, const Decl *Parent,
case Stmt::OMPForDirectiveClass:
K = CXCursor_OMPForDirective;
break;
+ case Stmt::OMPForSimdDirectiveClass:
+ K = CXCursor_OMPForSimdDirective;
+ break;
case Stmt::OMPSectionsDirectiveClass:
K = CXCursor_OMPSectionsDirective;
break;
@@ -544,6 +550,9 @@ CXCursor cxcursor::MakeCXCursor(const Stmt *S, const Decl *Parent,
case Stmt::OMPParallelForDirectiveClass:
K = CXCursor_OMPParallelForDirective;
break;
+ case Stmt::OMPParallelForSimdDirectiveClass:
+ K = CXCursor_OMPParallelForSimdDirective;
+ break;
case Stmt::OMPParallelSectionsDirectiveClass:
K = CXCursor_OMPParallelSectionsDirective;
break;
@@ -562,6 +571,18 @@ CXCursor cxcursor::MakeCXCursor(const Stmt *S, const Decl *Parent,
case Stmt::OMPFlushDirectiveClass:
K = CXCursor_OMPFlushDirective;
break;
+ case Stmt::OMPOrderedDirectiveClass:
+ K = CXCursor_OMPOrderedDirective;
+ break;
+ case Stmt::OMPAtomicDirectiveClass:
+ K = CXCursor_OMPAtomicDirective;
+ break;
+ case Stmt::OMPTargetDirectiveClass:
+ K = CXCursor_OMPTargetDirective;
+ break;
+ case Stmt::OMPTeamsDirectiveClass:
+ K = CXCursor_OMPTeamsDirective;
+ break;
}
CXCursor C = { K, 0, { Parent, S, TU } };
@@ -1055,6 +1076,140 @@ CXCursor clang_Cursor_getArgument(CXCursor C, unsigned i) {
return clang_getNullCursor();
}
+int clang_Cursor_getNumTemplateArguments(CXCursor C) {
+ if (clang_getCursorKind(C) != CXCursor_FunctionDecl) {
+ return -1;
+ }
+
+ const FunctionDecl *FD = llvm::dyn_cast_or_null<clang::FunctionDecl>(
+ getCursorDecl(C));
+ if (!FD) {
+ return -1;
+ }
+
+ const FunctionTemplateSpecializationInfo* SpecInfo =
+ FD->getTemplateSpecializationInfo();
+ if (!SpecInfo) {
+ return -1;
+ }
+
+ return SpecInfo->TemplateArguments->size();
+}
+
+enum CXGetTemplateArgumentStatus {
+ /** \brief The operation completed successfully */
+ CXGetTemplateArgumentStatus_Success = 0,
+
+ /** \brief The specified cursor did not represent a FunctionDecl. */
+ CXGetTemplateArgumentStatus_CursorNotFunctionDecl = -1,
+
+ /** \brief The specified cursor was not castable to a FunctionDecl. */
+ CXGetTemplateArgumentStatus_BadFunctionDeclCast = -2,
+
+ /** \brief A NULL FunctionTemplateSpecializationInfo was retrieved. */
+ CXGetTemplateArgumentStatus_NullTemplSpecInfo = -3,
+
+ /** \brief An invalid (OOB) argument index was specified */
+ CXGetTemplateArgumentStatus_InvalidIndex = -4
+};
+
+static int clang_Cursor_getTemplateArgument(
+ CXCursor C, unsigned I, TemplateArgument *TA) {
+ if (clang_getCursorKind(C) != CXCursor_FunctionDecl) {
+ return CXGetTemplateArgumentStatus_CursorNotFunctionDecl;
+ }
+
+ const FunctionDecl *FD = llvm::dyn_cast_or_null<clang::FunctionDecl>(
+ getCursorDecl(C));
+ if (!FD) {
+ return CXGetTemplateArgumentStatus_BadFunctionDeclCast;
+ }
+
+ const FunctionTemplateSpecializationInfo* SpecInfo =
+ FD->getTemplateSpecializationInfo();
+ if (!SpecInfo) {
+ return CXGetTemplateArgumentStatus_NullTemplSpecInfo;
+ }
+
+ if (I >= SpecInfo->TemplateArguments->size()) {
+ return CXGetTemplateArgumentStatus_InvalidIndex;
+ }
+
+ *TA = SpecInfo->TemplateArguments->get(I);
+ return 0;
+}
+
+enum CXTemplateArgumentKind clang_Cursor_getTemplateArgumentKind(CXCursor C,
+ unsigned I) {
+ TemplateArgument TA;
+ if (clang_Cursor_getTemplateArgument(C, I, &TA)) {
+ return CXTemplateArgumentKind_Invalid;
+ }
+
+ switch (TA.getKind()) {
+ case TemplateArgument::Null: return CXTemplateArgumentKind_Null;
+ case TemplateArgument::Type: return CXTemplateArgumentKind_Type;
+ case TemplateArgument::Declaration:
+ return CXTemplateArgumentKind_Declaration;
+ case TemplateArgument::NullPtr: return CXTemplateArgumentKind_NullPtr;
+ case TemplateArgument::Integral: return CXTemplateArgumentKind_Integral;
+ case TemplateArgument::Template: return CXTemplateArgumentKind_Template;
+ case TemplateArgument::TemplateExpansion:
+ return CXTemplateArgumentKind_TemplateExpansion;
+ case TemplateArgument::Expression: return CXTemplateArgumentKind_Expression;
+ case TemplateArgument::Pack: return CXTemplateArgumentKind_Pack;
+ }
+
+ return CXTemplateArgumentKind_Invalid;
+}
+
+CXType clang_Cursor_getTemplateArgumentType(CXCursor C, unsigned I) {
+ TemplateArgument TA;
+ if (clang_Cursor_getTemplateArgument(C, I, &TA) !=
+ CXGetTemplateArgumentStatus_Success) {
+ return cxtype::MakeCXType(QualType(), getCursorTU(C));
+ }
+
+ if (TA.getKind() != TemplateArgument::Type) {
+ return cxtype::MakeCXType(QualType(), getCursorTU(C));
+ }
+
+ return cxtype::MakeCXType(TA.getAsType(), getCursorTU(C));
+}
+
+long long clang_Cursor_getTemplateArgumentValue(CXCursor C, unsigned I) {
+ TemplateArgument TA;
+ if (clang_Cursor_getTemplateArgument(C, I, &TA) !=
+ CXGetTemplateArgumentStatus_Success) {
+ assert(0 && "Unable to retrieve TemplateArgument");
+ return 0;
+ }
+
+ if (TA.getKind() != TemplateArgument::Integral) {
+ assert(0 && "Passed template argument is not Integral");
+ return 0;
+ }
+
+ return TA.getAsIntegral().getSExtValue();
+}
+
+unsigned long long clang_Cursor_getTemplateArgumentUnsignedValue(CXCursor C,
+ unsigned I) {
+ TemplateArgument TA;
+ if (clang_Cursor_getTemplateArgument(C, I, &TA) !=
+ CXGetTemplateArgumentStatus_Success) {
+ assert(0 && "Unable to retrieve TemplateArgument");
+ return 0;
+ }
+
+ if (TA.getKind() != TemplateArgument::Integral) {
+ assert(0 && "Passed template argument is not Integral");
+ return 0;
+ }
+
+ return TA.getAsIntegral().getZExtValue();
+}
+
} // end: extern "C"
//===----------------------------------------------------------------------===//
@@ -1262,8 +1417,16 @@ int clang_Cursor_isDynamicCall(CXCursor C) {
if (!E)
return 0;
- if (const ObjCMessageExpr *MsgE = dyn_cast<ObjCMessageExpr>(E))
- return MsgE->getReceiverKind() == ObjCMessageExpr::Instance;
+ if (const ObjCMessageExpr *MsgE = dyn_cast<ObjCMessageExpr>(E)) {
+ if (MsgE->getReceiverKind() != ObjCMessageExpr::Instance)
+ return false;
+ if (auto *RecE = dyn_cast<ObjCMessageExpr>(
+ MsgE->getInstanceReceiver()->IgnoreParenCasts())) {
+ if (RecE->getMethodFamily() == OMF_alloc)
+ return false;
+ }
+ return true;
+ }
const MemberExpr *ME = nullptr;
if (isa<MemberExpr>(E))