https://github.com/DeinAlptraum updated 
https://github.com/llvm/llvm-project/pull/132377

>From c433f194600d72a3902c4eed304439d6e3f2f62b Mon Sep 17 00:00:00 2001
From: Mathias Stearn <redbeard0...@gmail.com>
Date: Thu, 19 Dec 2024 16:22:04 +0100
Subject: [PATCH 1/3] [libclang/python] Add some bindings to the Cursor
 interface

Make Cursor hashable
Add Cursor.has_attr()
Add Cursor.specialized_template
---
 clang/bindings/python/clang/cindex.py         | 17 ++++++++
 .../python/tests/cindex/test_cursor.py        | 40 +++++++++++++++++++
 clang/docs/ReleaseNotes.rst                   |  6 +++
 3 files changed, 63 insertions(+)

diff --git a/clang/bindings/python/clang/cindex.py 
b/clang/bindings/python/clang/cindex.py
index 879a0a3c5c58c..090ee899ad60e 100644
--- a/clang/bindings/python/clang/cindex.py
+++ b/clang/bindings/python/clang/cindex.py
@@ -1561,6 +1561,9 @@ def __eq__(self, other):
     def __ne__(self, other):
         return not self.__eq__(other)
 
+    def __hash__(self) -> int:
+        return self.hash
+
     def is_definition(self):
         """
         Returns true if the declaration pointed at by the cursor is also a
@@ -2035,6 +2038,13 @@ def lexical_parent(self):
 
         return self._lexical_parent
 
+    @property
+    def specialized_template(self) -> Cursor | None:
+        """Return the primary template that this cursor is a specialization 
of, if any."""
+        return Cursor.from_cursor_result(
+            conf.lib.clang_getSpecializedCursorTemplate(self), self
+        )
+
     @property
     def translation_unit(self):
         """Returns the TranslationUnit to which this Cursor belongs."""
@@ -2178,6 +2188,12 @@ def get_bitfield_width(self):
         """
         return conf.lib.clang_getFieldDeclBitWidth(self)  # type: ignore 
[no-any-return]
 
+    def has_attrs(self) -> bool:
+        """
+        Determine whether the given cursor has any attributes.
+        """
+        return bool(conf.lib.clang_Cursor_hasAttrs(self))
+
     @staticmethod
     def from_result(res, arg):
         assert isinstance(res, Cursor)
@@ -3932,6 +3948,7 @@ def set_property(self, property, value):
     ("clang_getCursorType", [Cursor], Type),
     ("clang_getCursorUSR", [Cursor], _CXString),
     ("clang_Cursor_getMangling", [Cursor], _CXString),
+    ("clang_Cursor_hasAttrs", [Cursor], c_uint),
     # ("clang_getCXTUResourceUsage",
     #  [TranslationUnit],
     #  CXTUResourceUsage),
diff --git a/clang/bindings/python/tests/cindex/test_cursor.py 
b/clang/bindings/python/tests/cindex/test_cursor.py
index c6aa65ce3c29f..9947f551cc2f8 100644
--- a/clang/bindings/python/tests/cindex/test_cursor.py
+++ b/clang/bindings/python/tests/cindex/test_cursor.py
@@ -4,6 +4,7 @@
     AvailabilityKind,
     BinaryOperator,
     Config,
+    Cursor,
     CursorKind,
     PrintingPolicy,
     PrintingPolicyProperty,
@@ -995,3 +996,42 @@ def test_pretty_print(self):
         pp.set_property(PrintingPolicyProperty.Bool, False)
         self.assertEqual(pp.get_property(PrintingPolicyProperty.Bool), False)
         self.assertEqual(f.pretty_printed(pp), "void f(_Bool x) {\n}\n")
+
+    def test_has_attrs(self):
+        tu = get_tu(
+            """
+struct A;
+struct A final {};
+
+struct B;
+struct B {};
+""",
+            lang="cpp",
+        )
+        A = get_cursor(tu, "A")
+        B = get_cursor(tu, "B")
+        self.assertTrue(A.get_definition().has_attrs())
+        self.assertFalse(B.get_definition().has_attrs())
+
+    def test_hash(self):
+        def accumulate_cursors(cursor: Cursor, all_cursors: list[Cursor]):
+            all_cursors.append(cursor)
+            for child in cursor.get_children():
+                all_cursors = accumulate_cursors(child, all_cursors)
+            return all_cursors
+
+        tu = get_tu(kInput)
+        all_cursors = accumulate_cursors(tu.cursor, [])
+        cursor_hashes = set()
+        for cursor in all_cursors:
+            self.assertNotIn(hash(cursor), cursor_hashes)
+            cursor_hashes.add(hash(cursor))
+
+    def test_specialized_template(self):
+        tu = get_tu(kTemplateArgTest, lang="cpp")
+        foos = get_cursors(tu, "foo")
+        prime_foo = foos[1].specialized_template
+
+        self.assertNotEqual(foos[0], foos[1])
+        self.assertEqual(foos[0], prime_foo)
+        self.assertIsNone(tu.cursor.specialized_template)
diff --git a/clang/docs/ReleaseNotes.rst b/clang/docs/ReleaseNotes.rst
index a25808e36bd51..ab68be3702840 100644
--- a/clang/docs/ReleaseNotes.rst
+++ b/clang/docs/ReleaseNotes.rst
@@ -442,6 +442,12 @@ Sanitizers
 
 Python Binding Changes
 ----------------------
+- Made ``Cursor`` hashable.
+- Added ``Cursor.has_attrs``, a binding for ``clang_Cursor_hasAttrs``, to check
+  whether a cursor has any attributes.
+- Added ``Cursor.specialized_template``, a binding for
+  ``clang_getSpecializedCursorTemplate``, to retrieve the primary template that
+  the cursor is a specialization of.
 - Added ``Type.get_methods``, a binding for ``clang_visitCXXMethods``, which
   allows visiting the methods of a class.
 

>From 1160d18e60f92dfe0f05493150849af1bc5b8d48 Mon Sep 17 00:00:00 2001
From: Jannick Kremer <jannick.kre...@mailbox.org>
Date: Fri, 21 Mar 2025 20:53:33 +0900
Subject: [PATCH 2/3] Reorder new tests

---
 .../python/tests/cindex/test_cursor.py        | 28 +++++++++----------
 1 file changed, 14 insertions(+), 14 deletions(-)

diff --git a/clang/bindings/python/tests/cindex/test_cursor.py 
b/clang/bindings/python/tests/cindex/test_cursor.py
index 9947f551cc2f8..7b791380526e6 100644
--- a/clang/bindings/python/tests/cindex/test_cursor.py
+++ b/clang/bindings/python/tests/cindex/test_cursor.py
@@ -997,6 +997,20 @@ def test_pretty_print(self):
         self.assertEqual(pp.get_property(PrintingPolicyProperty.Bool), False)
         self.assertEqual(f.pretty_printed(pp), "void f(_Bool x) {\n}\n")
 
+    def test_hash(self):
+        def accumulate_cursors(cursor: Cursor, all_cursors: list[Cursor]):
+            all_cursors.append(cursor)
+            for child in cursor.get_children():
+                all_cursors = accumulate_cursors(child, all_cursors)
+            return all_cursors
+
+        tu = get_tu(kInput)
+        all_cursors = accumulate_cursors(tu.cursor, [])
+        cursor_hashes = set()
+        for cursor in all_cursors:
+            self.assertNotIn(hash(cursor), cursor_hashes)
+            cursor_hashes.add(hash(cursor))
+
     def test_has_attrs(self):
         tu = get_tu(
             """
@@ -1013,20 +1027,6 @@ def test_has_attrs(self):
         self.assertTrue(A.get_definition().has_attrs())
         self.assertFalse(B.get_definition().has_attrs())
 
-    def test_hash(self):
-        def accumulate_cursors(cursor: Cursor, all_cursors: list[Cursor]):
-            all_cursors.append(cursor)
-            for child in cursor.get_children():
-                all_cursors = accumulate_cursors(child, all_cursors)
-            return all_cursors
-
-        tu = get_tu(kInput)
-        all_cursors = accumulate_cursors(tu.cursor, [])
-        cursor_hashes = set()
-        for cursor in all_cursors:
-            self.assertNotIn(hash(cursor), cursor_hashes)
-            cursor_hashes.add(hash(cursor))
-
     def test_specialized_template(self):
         tu = get_tu(kTemplateArgTest, lang="cpp")
         foos = get_cursors(tu, "foo")

>From 22edb94303a7358425906ca577d7f65e19cef072 Mon Sep 17 00:00:00 2001
From: Jannick Kremer <jannick.kre...@mailbox.org>
Date: Sat, 22 Mar 2025 18:34:03 +0900
Subject: [PATCH 3/3] Fix formatting Adapt global variable names

---
 clang/bindings/python/tests/cindex/test_cursor.py | 7 ++++---
 1 file changed, 4 insertions(+), 3 deletions(-)

diff --git a/clang/bindings/python/tests/cindex/test_cursor.py 
b/clang/bindings/python/tests/cindex/test_cursor.py
index df363c392b097..db3c408439eb5 100644
--- a/clang/bindings/python/tests/cindex/test_cursor.py
+++ b/clang/bindings/python/tests/cindex/test_cursor.py
@@ -998,13 +998,14 @@ def test_pretty_print(self):
         self.assertEqual(f.pretty_printed(pp), "void f(_Bool x) {\n}\n")
 
     def test_hash(self):
-        def accumulate_cursors(cursor: Cursor, all_cursors: list[Cursor]):
+
+        def accumulate_cursors(cursor: Cursor, all_cursors: list):
             all_cursors.append(cursor)
             for child in cursor.get_children():
                 all_cursors = accumulate_cursors(child, all_cursors)
             return all_cursors
 
-        tu = get_tu(kInput)
+        tu = get_tu(children_test)
         all_cursors = accumulate_cursors(tu.cursor, [])
         cursor_hashes = set()
         for cursor in all_cursors:
@@ -1028,7 +1029,7 @@ def test_has_attrs(self):
         self.assertFalse(B.get_definition().has_attrs())
 
     def test_specialized_template(self):
-        tu = get_tu(kTemplateArgTest, lang="cpp")
+        tu = get_tu(template_arg_test, lang="cpp")
         foos = get_cursors(tu, "foo")
         prime_foo = foos[1].specialized_template
 

_______________________________________________
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits

Reply via email to