[cfe-commits] r112600 - in /cfe/trunk: include/clang-c/Index.h test/Index/load-classes.cpp tools/libclang/CIndex.cpp tools/libclang/CXCursor.cpp

Douglas Gregor dgregor at apple.com
Tue Aug 31 07:41:23 PDT 2010


Author: dgregor
Date: Tue Aug 31 09:41:23 2010
New Revision: 112600

URL: http://llvm.org/viewvc/llvm-project?rev=112600&view=rev
Log:
libclang indexing support for C++ constructors, destructors, and
conversion functions. This introduces new cursor kinds for these three
C++ entities, and reworks visitation of function declarations so that
we get type-source information for the names.

Added:
    cfe/trunk/test/Index/load-classes.cpp   (with props)
Modified:
    cfe/trunk/include/clang-c/Index.h
    cfe/trunk/tools/libclang/CIndex.cpp
    cfe/trunk/tools/libclang/CXCursor.cpp

Modified: cfe/trunk/include/clang-c/Index.h
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/include/clang-c/Index.h?rev=112600&r1=112599&r2=112600&view=diff
==============================================================================
--- cfe/trunk/include/clang-c/Index.h (original)
+++ cfe/trunk/include/clang-c/Index.h Tue Aug 31 09:41:23 2010
@@ -976,9 +976,14 @@
   CXCursor_Namespace                     = 22,
   /** \brief A linkage specification, e.g. 'extern "C"'. */
   CXCursor_LinkageSpec                   = 23,
-
+  /** \brief A C++ constructor. */
+  CXCursor_Constructor                   = 24,
+  /** \brief A C++ destructor. */
+  CXCursor_Destructor                    = 25,
+  /** \brief A C++ conversion function. */
+  CXCursor_ConversionFunction            = 26,
   CXCursor_FirstDecl                     = CXCursor_UnexposedDecl,
-  CXCursor_LastDecl                      = CXCursor_LinkageSpec,
+  CXCursor_LastDecl                      = CXCursor_ConversionFunction,
 
   /* References */
   CXCursor_FirstRef                      = 40, /* Decl references */

Added: cfe/trunk/test/Index/load-classes.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/test/Index/load-classes.cpp?rev=112600&view=auto
==============================================================================
--- cfe/trunk/test/Index/load-classes.cpp (added)
+++ cfe/trunk/test/Index/load-classes.cpp Tue Aug 31 09:41:23 2010
@@ -0,0 +1,22 @@
+// Test is line- and column-sensitive; see below.
+
+struct X {
+  X(int value);
+  X(const X& x);
+  ~X();
+  operator X*();
+};
+
+// RUN: c-index-test -test-load-source all %s | FileCheck %s
+// CHECK: load-classes.cpp:3:8: StructDecl=X:3:8 (Definition) Extent=[3:1 - 8:2]
+// CHECK: load-classes.cpp:4:3: CXXConstructor=X:4:3 Extent=[4:3 - 4:15]
+// FIXME: missing TypeRef in the constructor name
+// CHECK: load-classes.cpp:4:9: ParmDecl=value:4:9 (Definition) Extent=[4:5 - 4:14]
+// CHECK: load-classes.cpp:5:3: CXXConstructor=X:5:3 Extent=[5:3 - 5:16]
+// FIXME: missing TypeRef in the constructor name
+// CHECK: load-classes.cpp:5:14: ParmDecl=x:5:14 (Definition) Extent=[5:11 - 5:15]
+// CHECK: load-classes.cpp:5:11: TypeRef=struct X:3:8 Extent=[5:11 - 5:12]
+// CHECK: load-classes.cpp:6:3: CXXDestructor=~X:6:3 Extent=[6:3 - 6:7]
+// FIXME: missing TypeRef in the destructor name
+// CHECK: load-classes.cpp:7:3: CXXConversion=operator struct X *:7:3 Extent=[7:3 - 7:16]
+// CHECK: load-classes.cpp:7:12: TypeRef=struct X:3:8 Extent=[7:12 - 7:13]

Propchange: cfe/trunk/test/Index/load-classes.cpp
------------------------------------------------------------------------------
    svn:eol-style = native

Propchange: cfe/trunk/test/Index/load-classes.cpp
------------------------------------------------------------------------------
    svn:keywords = Id

Propchange: cfe/trunk/test/Index/load-classes.cpp
------------------------------------------------------------------------------
    svn:mime-type = text/plain

Modified: cfe/trunk/tools/libclang/CIndex.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/tools/libclang/CIndex.cpp?rev=112600&r1=112599&r2=112600&view=diff
==============================================================================
--- cfe/trunk/tools/libclang/CIndex.cpp (original)
+++ cfe/trunk/tools/libclang/CIndex.cpp Tue Aug 31 09:41:23 2010
@@ -312,8 +312,11 @@
   bool VisitLinkageSpecDecl(LinkageSpecDecl *D);
   bool VisitNamespaceDecl(NamespaceDecl *D);
 
+  // Name visitor
+  bool VisitDeclarationNameInfo(DeclarationNameInfo Name);
+  
   // Type visitors
-  // FIXME: QualifiedTypeLoc doesn't provide any location information
+  bool VisitQualifiedTypeLoc(QualifiedTypeLoc TL);
   bool VisitBuiltinTypeLoc(BuiltinTypeLoc TL);
   bool VisitTypedefTypeLoc(TypedefTypeLoc TL);
   bool VisitUnresolvedUsingTypeLoc(UnresolvedUsingTypeLoc TL);
@@ -327,7 +330,7 @@
   bool VisitMemberPointerTypeLoc(MemberPointerTypeLoc TL);
   bool VisitLValueReferenceTypeLoc(LValueReferenceTypeLoc TL);
   bool VisitRValueReferenceTypeLoc(RValueReferenceTypeLoc TL);
-  bool VisitFunctionTypeLoc(FunctionTypeLoc TL);
+  bool VisitFunctionTypeLoc(FunctionTypeLoc TL, bool SkipResultType = false);
   bool VisitArrayTypeLoc(ArrayTypeLoc TL);
   // FIXME: Implement for TemplateSpecializationTypeLoc
   // FIXME: Implement visitors here when the unimplemented TypeLocs get
@@ -605,9 +608,34 @@
 }
 
 bool CursorVisitor::VisitFunctionDecl(FunctionDecl *ND) {
-  if (VisitDeclaratorDecl(ND))
-    return true;
-
+  if (TypeSourceInfo *TSInfo = ND->getTypeSourceInfo()) {
+    // Visit the function declaration's syntactic components in the order
+    // written. This requires a bit of work.
+    TypeLoc TL = TSInfo->getTypeLoc();
+    FunctionTypeLoc *FTL = dyn_cast<FunctionTypeLoc>(&TL);
+    
+    // If we have a function declared directly (without the use of a typedef),
+    // visit just the return type. Otherwise, just visit the function's type
+    // now.
+    if ((FTL && !isa<CXXConversionDecl>(ND) && Visit(FTL->getResultLoc())) ||
+        (!FTL && Visit(TL)))
+      return true;
+    
+    // FIXME: Visit the nested-name-specifier, if present.
+    
+    // Visit the declaration name.
+    if (VisitDeclarationNameInfo(ND->getNameInfo()))
+      return true;
+    
+    // FIXME: Visit explicitly-specified template arguments!
+    
+    // Visit the function parameters, if we have a function type.
+    if (FTL && VisitFunctionTypeLoc(*FTL, true))
+      return true;
+    
+    // FIXME: Attributes?
+  }
+  
   if (ND->isThisDeclarationADefinition() &&
       Visit(MakeCXCursor(ND->getBody(), StmtParent, TU)))
     return true;
@@ -786,10 +814,39 @@
   return VisitDeclContext(D);
 }
 
+bool CursorVisitor::VisitDeclarationNameInfo(DeclarationNameInfo Name) {
+  switch (Name.getName().getNameKind()) {
+  case clang::DeclarationName::Identifier:
+  case clang::DeclarationName::CXXLiteralOperatorName:
+  case clang::DeclarationName::CXXOperatorName:
+  case clang::DeclarationName::CXXUsingDirective:
+    return false;
+      
+  case clang::DeclarationName::CXXConstructorName:
+  case clang::DeclarationName::CXXDestructorName:
+  case clang::DeclarationName::CXXConversionFunctionName:
+    if (TypeSourceInfo *TSInfo = Name.getNamedTypeInfo())
+      return Visit(TSInfo->getTypeLoc());
+    return false;
+
+  case clang::DeclarationName::ObjCZeroArgSelector:
+  case clang::DeclarationName::ObjCOneArgSelector:
+  case clang::DeclarationName::ObjCMultiArgSelector:
+    // FIXME: Per-identifier location info?
+    return false;
+  }
+  
+  return false;
+}
+
 bool CursorVisitor::VisitLinkageSpecDecl(LinkageSpecDecl *D) {
   return VisitDeclContext(D);
 }
 
+bool CursorVisitor::VisitQualifiedTypeLoc(QualifiedTypeLoc TL) {
+  return Visit(TL.getUnqualifiedLoc());
+}
+
 bool CursorVisitor::VisitBuiltinTypeLoc(BuiltinTypeLoc TL) {
   ASTContext &Context = TU->getASTContext();
 
@@ -905,8 +962,9 @@
   return Visit(TL.getPointeeLoc());
 }
 
-bool CursorVisitor::VisitFunctionTypeLoc(FunctionTypeLoc TL) {
-  if (Visit(TL.getResultLoc()))
+bool CursorVisitor::VisitFunctionTypeLoc(FunctionTypeLoc TL, 
+                                         bool SkipResultType) {
+  if (!SkipResultType && Visit(TL.getResultLoc()))
     return true;
 
   for (unsigned I = 0, N = TL.getNumArgs(); I != N; ++I)
@@ -1973,6 +2031,12 @@
     return createCXString("LinkageSpec");
   case CXCursor_CXXBaseSpecifier:
     return createCXString("C++ base class specifier");  
+  case CXCursor_Constructor:
+    return createCXString("CXXConstructor");
+  case CXCursor_Destructor:
+    return createCXString("CXXDestructor");
+  case CXCursor_ConversionFunction:
+    return createCXString("CXXConversion");
   }
 
   llvm_unreachable("Unhandled CXCursorKind");

Modified: cfe/trunk/tools/libclang/CXCursor.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/tools/libclang/CXCursor.cpp?rev=112600&r1=112599&r2=112600&view=diff
==============================================================================
--- cfe/trunk/tools/libclang/CXCursor.cpp (original)
+++ cfe/trunk/tools/libclang/CXCursor.cpp Tue Aug 31 09:41:23 2010
@@ -51,6 +51,9 @@
       return cast<ObjCMethodDecl>(D)->isInstanceMethod()
               ? CXCursor_ObjCInstanceMethodDecl : CXCursor_ObjCClassMethodDecl;
     case Decl::CXXMethod:          return CXCursor_CXXMethod;
+    case Decl::CXXConstructor:     return CXCursor_Constructor;
+    case Decl::CXXDestructor:      return CXCursor_Destructor;
+    case Decl::CXXConversion:      return CXCursor_ConversionFunction;
     case Decl::ObjCProperty:       return CXCursor_ObjCPropertyDecl;
     case Decl::ObjCProtocol:       return CXCursor_ObjCProtocolDecl;
     case Decl::ParmVar:            return CXCursor_ParmDecl;





More information about the cfe-commits mailing list