gdb/python: have PendingFrame methods accept keyword arguments
authorAndrew Burgess <aburgess@redhat.com>
Tue, 14 Mar 2023 11:43:14 +0000 (11:43 +0000)
committerAndrew Burgess <aburgess@redhat.com>
Thu, 6 Apr 2023 14:01:43 +0000 (15:01 +0100)
Update the two gdb.PendingFrame methods gdb.PendingFrame.read_register
and gdb.PendingFrame.create_unwind_info to accept keyword arguments.

There's no huge benefit for making this change, both of these methods
only take a single argument, so it is (maybe) less likely that a user
will take advantage of the keyword arguments in these cases, but I
think it's nice to be consistent, and I don't see any particular draw
backs to making this change.

For PendingFrame.read_register I've changed the argument name from
'reg' to 'register' in the documentation and used 'register' as the
argument name in GDB.  My preference for APIs is to use full words
where possible, and given we didn't support named arguments before
this change should not break any existing code.

There should be no user visible changes (for existing code) after this
commit.

Reviewed-By: Eli Zaretskii <eliz@gnu.org>
Reviewed-By: Tom Tromey <tom@tromey.com>
gdb/doc/python.texi
gdb/python/py-unwind.c
gdb/testsuite/gdb.python/py-unwind.py

index a4fd0095c43dd6b39b959fa933ac799e0ddd4a89..1315ddcacbcf3f0965e3bce6dc393a12a27a770f 100644 (file)
@@ -2756,11 +2756,11 @@ unwinding.
 An object passed to an unwinder (a @code{gdb.PendingFrame} instance)
 provides a method to read frame's registers:
 
-@defun PendingFrame.read_register (reg)
-This method returns the contents of the register @var{reg} in the
+@defun PendingFrame.read_register (register)
+This method returns the contents of @var{register} in the
 frame as a @code{gdb.Value} object.  For a description of the
-acceptable values of @var{reg} see
-@ref{gdbpy_frame_read_register,,Frame.read_register}.  If @var{reg}
+acceptable values of @var{register} see
+@ref{gdbpy_frame_read_register,,Frame.read_register}.  If @var{register}
 does not name a register for the current architecture, this method
 will throw an exception.
 
index 2e13b84eb126c66ae019431a70af4dc0f1075e6a..d83979bed2b3bb2fb481424952b1df003151aeb2 100644 (file)
@@ -443,16 +443,17 @@ pending_framepy_repr (PyObject *self)
    Returns the value of register REG as gdb.Value instance.  */
 
 static PyObject *
-pending_framepy_read_register (PyObject *self, PyObject *args)
+pending_framepy_read_register (PyObject *self, PyObject *args, PyObject *kw)
 {
   pending_frame_object *pending_frame = (pending_frame_object *) self;
   PENDING_FRAMEPY_REQUIRE_VALID (pending_frame);
 
-  int regnum;
   PyObject *pyo_reg_id;
+  static const char *keywords[] = { "register", nullptr };
+  if (!gdb_PyArg_ParseTupleAndKeywords (args, kw, "O", keywords, &pyo_reg_id))
+    return nullptr;
 
-  if (!PyArg_UnpackTuple (args, "read_register", 1, 1, &pyo_reg_id))
-    return NULL;
+  int regnum;
   if (!gdbpy_parse_register_id (pending_frame->gdbarch, pyo_reg_id, &regnum))
     return nullptr;
 
@@ -681,7 +682,8 @@ pending_framepy_function (PyObject *self, PyObject *args)
    PendingFrame.create_unwind_info (self, frameId) -> UnwindInfo.  */
 
 static PyObject *
-pending_framepy_create_unwind_info (PyObject *self, PyObject *args)
+pending_framepy_create_unwind_info (PyObject *self, PyObject *args,
+                                   PyObject *kw)
 {
   PyObject *pyo_frame_id;
   CORE_ADDR sp;
@@ -690,7 +692,9 @@ pending_framepy_create_unwind_info (PyObject *self, PyObject *args)
 
   PENDING_FRAMEPY_REQUIRE_VALID ((pending_frame_object *) self);
 
-  if (!PyArg_ParseTuple (args, "O:create_unwind_info", &pyo_frame_id))
+  static const char *keywords[] = { "frame_id", nullptr };
+  if (!gdb_PyArg_ParseTupleAndKeywords (args, kw, "O", keywords,
+                                       &pyo_frame_id))
     return nullptr;
 
   pyuw_get_attr_code code
@@ -1002,11 +1006,12 @@ gdbpy_initialize_unwind (void)
 
 static PyMethodDef pending_frame_object_methods[] =
 {
-  { "read_register", pending_framepy_read_register, METH_VARARGS,
+  { "read_register", (PyCFunction) pending_framepy_read_register,
+    METH_VARARGS | METH_KEYWORDS,
     "read_register (REG) -> gdb.Value\n"
     "Return the value of the REG in the frame." },
-  { "create_unwind_info",
-    pending_framepy_create_unwind_info, METH_VARARGS,
+  { "create_unwind_info", (PyCFunction) pending_framepy_create_unwind_info,
+    METH_VARARGS | METH_KEYWORDS,
     "create_unwind_info (FRAME_ID) -> gdb.UnwindInfo\n"
     "Construct UnwindInfo for this PendingFrame, using FRAME_ID\n"
     "to identify it." },
index 5853abc7486c95bbc8abc76b48d30992607915e6..201b629f9fe83cb3f53725af603f6a13d7c3735c 100644 (file)
@@ -99,7 +99,7 @@ class TestUnwinder(Unwinder):
                 read_register_error = str(ve)
 
             frame_id = FrameId(
-                pending_frame.read_register(TestUnwinder.AMD64_RSP),
+                pending_frame.read_register(register=TestUnwinder.AMD64_RSP),
                 pending_frame.read_register(TestUnwinder.AMD64_RIP),
             )
             unwind_info = pending_frame.create_unwind_info(frame_id)
@@ -156,7 +156,7 @@ class simple_unwinder(Unwinder):
             captured_pending_frame = pending_frame
             captured_pending_frame_repr = repr(pending_frame)
             fid = FrameId(self._sp, self._pc)
-            uw = pending_frame.create_unwind_info(fid)
+            uw = pending_frame.create_unwind_info(frame_id=fid)
             uw.add_saved_register("rip", gdb.Value(0x123))
             uw.add_saved_register("rbp", gdb.Value(0x456))
             uw.add_saved_register("rsp", gdb.Value(0x789))