]> granicus.if.org Git - clang/commitdiff
Improve the Python bindings for libclang in a few ways, from Eli
authorDouglas Gregor <dgregor@apple.com>
Wed, 6 Jul 2011 03:00:34 +0000 (03:00 +0000)
committerDouglas Gregor <dgregor@apple.com>
Wed, 6 Jul 2011 03:00:34 +0000 (03:00 +0000)
Bendersky. Specifically:

* Implemented a new function in libclang: clang_isAttribute

* Fixing TranslationUnit.get_includes to only go through the argument
* buffer when it contains something. This fixed a crash on Windows

* clang_getFileName returns CXString, not char*. Made appropriate
* fixes in cindex.py - now the relevant tests pass and we can see the
* full locations correctly again (previously there was garbage in
* place of the file name)
* Exposed clang_getCursorDisplayName to the python bindings

git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@134460 91177308-0d34-0410-b5e6-96231b3b80d8

bindings/python/clang/cindex.py
bindings/python/tests/cindex/test_cursor_kind.py
bindings/python/tests/cindex/test_translation_unit.py
include/clang-c/Index.h
tools/libclang/CIndex.cpp
tools/libclang/libclang.darwin.exports
tools/libclang/libclang.exports

index 08ad80234e09c9fd6984d046849dcf73afcd502f..8cadcaa7ad063aeb8723179bd95e71cfe16180b8 100644 (file)
@@ -321,6 +321,10 @@ class CursorKind(object):
         """Test if this is a statement kind."""
         return CursorKind_is_stmt(self)
 
+    def is_attribute(self):
+        """Test if this is an attribute kind."""
+        return CursorKind_is_attribute(self)
+
     def is_invalid(self):
         """Test if this is an invalid kind."""
         return CursorKind_is_inv(self)
@@ -978,8 +982,9 @@ class TranslationUnit(ClangObject):
         headers.
         """
         def visitor(fobj, lptr, depth, includes):
-            loc = lptr.contents
-            includes.append(FileInclusion(loc.file, File(fobj), loc, depth))
+            if depth > 0:
+                loc = lptr.contents
+                includes.append(FileInclusion(loc.file, File(fobj), loc, depth))
 
         # Automatically adapt CIndex/ctype pointers to python objects
         includes = []
@@ -1074,7 +1079,7 @@ class File(ClangObject):
     @property
     def name(self):
         """Return the complete file and path name of the file."""
-        return File_name(self)
+        return _CXString_getCString(File_name(self))
 
     @property
     def time(self):
@@ -1147,6 +1152,10 @@ CursorKind_is_stmt = lib.clang_isStatement
 CursorKind_is_stmt.argtypes = [CursorKind]
 CursorKind_is_stmt.restype = bool
 
+CursorKind_is_attribute = lib.clang_isAttribute
+CursorKind_is_attribute.argtypes = [CursorKind]
+CursorKind_is_attribute.restype = bool
+
 CursorKind_is_inv = lib.clang_isInvalid
 CursorKind_is_inv.argtypes = [CursorKind]
 CursorKind_is_inv.restype = bool
@@ -1183,6 +1192,11 @@ Cursor_spelling.argtypes = [Cursor]
 Cursor_spelling.restype = _CXString
 Cursor_spelling.errcheck = _CXString.from_result
 
+Cursor_displayname = lib.clang_getCursorDisplayName
+Cursor_displayname.argtypes = [Cursor]
+Cursor_displayname.restype = _CXString
+Cursor_displayname.errcheck = _CXString.from_result
+
 Cursor_loc = lib.clang_getCursorLocation
 Cursor_loc.argtypes = [Cursor]
 Cursor_loc.restype = SourceLocation
@@ -1253,7 +1267,7 @@ TranslationUnit_includes.argtypes = [TranslationUnit,
 # File Functions
 File_name = lib.clang_getFileName
 File_name.argtypes = [File]
-File_name.restype = c_char_p
+File_name.restype = _CXString
 
 File_time = lib.clang_getFileTime
 File_time.argtypes = [File]
index bdfa31855835507f6d17a3907653d50830ccc315..d7a1cfad8f946addf9679fee6dfaa30a5f2df43b 100644 (file)
@@ -18,10 +18,14 @@ def test_kind_groups():
 
     for k in CursorKind.get_all_kinds():
         group = [n for n in ('is_declaration', 'is_reference', 'is_expression',
-                             'is_statement', 'is_invalid')
+                             'is_statement', 'is_invalid', 'is_attribute')
                  if getattr(k, n)()]
 
-        if k == CursorKind.TRANSLATION_UNIT:
+        if k in (   CursorKind.TRANSLATION_UNIT,
+                    CursorKind.MACRO_DEFINITION,
+                    CursorKind.MACRO_INSTANTIATION,
+                    CursorKind.INCLUSION_DIRECTIVE,
+                    CursorKind.PREPROCESSING_DIRECTIVE):
             assert len(group) == 0
         else:
             assert len(group) == 1
index f130db6aeb068ea26c4030c6251dd402d188ba03..2e65d9518da0f57e5ad7c52811977ad2ad6eebb4 100644 (file)
@@ -58,24 +58,27 @@ def test_unsaved_files_2():
     spellings = [c.spelling for c in tu.cursor.get_children()]
     assert spellings[-1] == 'x'
 
+def normpaths_equal(path1, path2):
+    """ Compares two paths for equality after normalizing them with
+        os.path.normpath
+    """
+    return os.path.normpath(path1) == os.path.normpath(path2)
 
 def test_includes():
     def eq(expected, actual):
         if not actual.is_input_file:
-            return expected[0] == actual.source.name and \
-                   expected[1] == actual.include.name
+            return  normpaths_equal(expected[0], actual.source.name) and \
+                    normpaths_equal(expected[1], actual.include.name)
         else:
-            return expected[1] == actual.include.name
+            return normpaths_equal(expected[1], actual.include.name)
 
     src = os.path.join(kInputsDir, 'include.cpp')
     h1 = os.path.join(kInputsDir, "header1.h")
     h2 = os.path.join(kInputsDir, "header2.h")
     h3 = os.path.join(kInputsDir, "header3.h")
-    inc = [(None, src), (src, h1), (h1, h3), (src, h2), (h2, h3)]
+    inc = [(src, h1), (h1, h3), (src, h2), (h2, h3)]
 
     index = Index.create()
     tu = index.parse(src)
     for i in zip(inc, tu.get_includes()):
         assert eq(i[0], i[1])
-
-
index cb0b3c1babcb2d4a1369ce0422eabb466737867e..01e7bce6bd42f6ce6790d35b5b54d9613386b621 100644 (file)
@@ -1473,6 +1473,11 @@ CINDEX_LINKAGE unsigned clang_isExpression(enum CXCursorKind);
  */
 CINDEX_LINKAGE unsigned clang_isStatement(enum CXCursorKind);
 
+/**
+ * \brief Determine whether the given cursor kind represents an attribute.
+ */
+CINDEX_LINKAGE unsigned clang_isAttribute(enum CXCursorKind);
+
 /**
  * \brief Determine whether the given cursor kind represents an invalid
  * cursor.
index e4902e9035bb1d0b6287d53270ed1779bf20e07b..fc331d077a9e466d3aec203ffe515c53219526bc 100644 (file)
@@ -3562,6 +3562,10 @@ unsigned clang_isStatement(enum CXCursorKind K) {
   return K >= CXCursor_FirstStmt && K <= CXCursor_LastStmt;
 }
 
+unsigned clang_isAttribute(enum CXCursorKind K) {
+    return K >= CXCursor_FirstAttr && K <= CXCursor_LastAttr;
+}
+
 unsigned clang_isTranslationUnit(enum CXCursorKind K) {
   return K == CXCursor_TranslationUnit;
 }
index 85dfcb68685c61fc50032055dac12d2828c0970f..daada6d3f0531ec24169b27efd6401ae0d915aee 100644 (file)
@@ -112,6 +112,7 @@ _clang_getTranslationUnitSpelling
 _clang_getTypeDeclaration
 _clang_getTypeKindSpelling
 _clang_hashCursor
+_clang_isAttribute
 _clang_isConstQualifiedType
 _clang_isCursorDefinition
 _clang_isDeclaration
index 403cd67538c5d11cb3d02867cd71d25043f95a3d..0d27f6babb334b523e649e88408a773d0eae7a28 100644 (file)
@@ -112,6 +112,7 @@ clang_getTranslationUnitSpelling
 clang_getTypeDeclaration
 clang_getTypeKindSpelling
 clang_hashCursor
+clang_isAttribute
 clang_isConstQualifiedType
 clang_isCursorDefinition
 clang_isDeclaration