public inbox for gdb-patches@sourceware.org
 help / color / mirror / Atom feed
* [PATCH 4/7] py-symbol: Require a frame for lookup_symbol only when necessary
  2016-02-04 17:29 [PATCH 0/7] Python extension patchset jeffm
  2016-02-04 17:29 ` [PATCH 6/7] py-minsymbol: Add interface to access minimal_symbols jeffm
@ 2016-02-04 17:29 ` jeffm
  2016-02-05 12:17   ` Phil Muldoon
  2016-02-05 16:35   ` Phil Muldoon
  2016-02-04 17:29 ` [PATCH 1/7] check_types_equal: short circuit check if identical pointers are used jeffm
                   ` (4 subsequent siblings)
  6 siblings, 2 replies; 17+ messages in thread
From: jeffm @ 2016-02-04 17:29 UTC (permalink / raw)
  To: gdb-patches; +Cc: Jeff Mahoney

From: Jeff Mahoney <jeffm@suse.com>

gdbpy_lookup_symbol requires a frame prior to doing the symbol lookup but
a frame isn't necessary for many symbol types.  Calling
symbol_read_needs_frame will tell us if it's necessary but we need to
have already looked up the symbol to use it.  This patch puts the
lookup first and then only resolves the frame if one is required.

This allows us to lookup static symbols directly from python rather
than using gdb.eval_and_parse.
---
 gdb/python/py-symbol.c | 31 +++++++++++++++++--------------
 1 file changed, 17 insertions(+), 14 deletions(-)

diff --git a/gdb/python/py-symbol.c b/gdb/python/py-symbol.c
index cbbc9e2..c7f0ff8 100644
--- a/gdb/python/py-symbol.c
+++ b/gdb/python/py-symbol.c
@@ -382,14 +382,28 @@ gdbpy_lookup_symbol (PyObject *self, PyObject *args, PyObject *kw)
 
   if (block_obj)
     block = block_object_to_block (block_obj);
-  else
+
+  TRY
+    {
+      symbol = lookup_symbol (name, block, (domain_enum) domain,
+			      &is_a_field_of_this).symbol;
+    }
+  CATCH (except, RETURN_MASK_ALL)
+    {
+      GDB_PY_HANDLE_EXCEPTION (except);
+    }
+  END_CATCH
+
+  if (symbol && !block)
     {
       struct frame_info *selected_frame;
 
       TRY
 	{
-	  selected_frame = get_selected_frame (_("No frame selected."));
-	  block = get_frame_block (selected_frame, NULL);
+	  if (symbol_read_needs_frame(symbol)) {
+	    selected_frame = get_selected_frame (_("No frame selected."));
+	    block = get_frame_block (selected_frame, NULL);
+	  }
 	}
       CATCH (except, RETURN_MASK_ALL)
 	{
@@ -398,17 +412,6 @@ gdbpy_lookup_symbol (PyObject *self, PyObject *args, PyObject *kw)
       END_CATCH
     }
 
-  TRY
-    {
-      symbol = lookup_symbol (name, block, (domain_enum) domain,
-			      &is_a_field_of_this).symbol;
-    }
-  CATCH (except, RETURN_MASK_ALL)
-    {
-      GDB_PY_HANDLE_EXCEPTION (except);
-    }
-  END_CATCH
-
   ret_tuple = PyTuple_New (2);
   if (!ret_tuple)
     return NULL;
-- 
2.1.4

^ permalink raw reply	[flat|nested] 17+ messages in thread

* [PATCH 0/7] Python extension patchset
@ 2016-02-04 17:29 jeffm
  2016-02-04 17:29 ` [PATCH 6/7] py-minsymbol: Add interface to access minimal_symbols jeffm
                   ` (6 more replies)
  0 siblings, 7 replies; 17+ messages in thread
From: jeffm @ 2016-02-04 17:29 UTC (permalink / raw)
  To: gdb-patches; +Cc: Jeff Mahoney

From: Jeff Mahoney <jeffm@suse.com>

Hi all -

Here's the cleaned up version of my python extension patchset.

-Jeff


Jeff Mahoney (7):
  check_types_equal: short circuit check if identical pointers are used
  py-value: properly handle unsigned and pointer types
  py-symbol: use Py_RETURN_NONE instead of open coding it
  py-symbol: Require a frame for lookup_symbol only when necessary
  py-symbol: export section name
  py-minsymbol: Add interface to access minimal_symbols
  py-regcache: Add interface to regcache

 gdb/Makefile.in              |  12 ++
 gdb/gdbtypes.c               |   3 +
 gdb/python/py-infthread.c    |  31 ++++
 gdb/python/py-minsymbol.c    | 390 +++++++++++++++++++++++++++++++++++++++++++
 gdb/python/py-regcache.c     | 367 ++++++++++++++++++++++++++++++++++++++++
 gdb/python/py-symbol.c       |  60 +++++--
 gdb/python/py-value.c        |  12 ++
 gdb/python/python-internal.h |  12 ++
 gdb/python/python.c          |   8 +-
 9 files changed, 876 insertions(+), 19 deletions(-)
 create mode 100644 gdb/python/py-minsymbol.c
 create mode 100644 gdb/python/py-regcache.c

-- 
2.1.4

^ permalink raw reply	[flat|nested] 17+ messages in thread

* [PATCH 6/7] py-minsymbol: Add interface to access minimal_symbols
  2016-02-04 17:29 [PATCH 0/7] Python extension patchset jeffm
@ 2016-02-04 17:29 ` jeffm
  2016-02-05 12:25   ` Phil Muldoon
  2016-02-05 16:43   ` Phil Muldoon
  2016-02-04 17:29 ` [PATCH 4/7] py-symbol: Require a frame for lookup_symbol only when necessary jeffm
                   ` (5 subsequent siblings)
  6 siblings, 2 replies; 17+ messages in thread
From: jeffm @ 2016-02-04 17:29 UTC (permalink / raw)
  To: gdb-patches; +Cc: Jeff Mahoney

From: Jeff Mahoney <jeffm@suse.com>

This patch adds a new gdb.MinSymbol object to export the minimal_symbol
interface.  These objects can be resolved using a new
gdb.lookup_minimal_symbol call.
---
 gdb/Makefile.in              |   6 +
 gdb/python/py-minsymbol.c    | 390 +++++++++++++++++++++++++++++++++++++++++++
 gdb/python/python-internal.h |   6 +
 gdb/python/python.c          |   5 +
 4 files changed, 407 insertions(+)
 create mode 100644 gdb/python/py-minsymbol.c

diff --git a/gdb/Makefile.in b/gdb/Makefile.in
index 3eadbbc..c2f7eef 100644
--- a/gdb/Makefile.in
+++ b/gdb/Makefile.in
@@ -400,6 +400,7 @@ SUBDIR_PYTHON_OBS = \
 	py-infthread.o \
 	py-lazy-string.o \
 	py-linetable.o \
+	py-minsymbol.o \
 	py-newobjfileevent.o \
 	py-objfile.o \
 	py-param.o \
@@ -440,6 +441,7 @@ SUBDIR_PYTHON_SRCS = \
 	python/py-infthread.c \
 	python/py-lazy-string.c \
 	python/py-linetable.c \
+	python/py-minsymbol.c \
 	python/py-newobjfileevent.c \
 	python/py-objfile.c \
 	python/py-param.c \
@@ -2635,6 +2637,10 @@ py-linetable.o: $(srcdir)/python/py-linetable.c
 	$(COMPILE) $(PYTHON_CFLAGS) $(srcdir)/python/py-linetable.c
 	$(POSTCOMPILE)
 
+py-minsymbol.o: $(srcdir)/python/py-minsymbol.c
+	$(COMPILE) $(PYTHON_CFLAGS) $(srcdir)/python/py-minsymbol.c
+	$(POSTCOMPILE)
+
 py-newobjfileevent.o: $(srcdir)/python/py-newobjfileevent.c
 	$(COMPILE) $(PYTHON_CFLAGS) $(srcdir)/python/py-newobjfileevent.c
 	$(POSTCOMPILE)
diff --git a/gdb/python/py-minsymbol.c b/gdb/python/py-minsymbol.c
new file mode 100644
index 0000000..d8b56bc
--- /dev/null
+++ b/gdb/python/py-minsymbol.c
@@ -0,0 +1,390 @@
+/* Python interface to minsymbols.
+
+   Copyright (C) 2008-2013 Free Software Foundation, Inc.
+
+   This file is part of GDB.
+
+   This program is free software; you can redistribute it and/or modify
+   it under the terms of the GNU General Public License as published by
+   the Free Software Foundation; either version 3 of the License, or
+   (at your option) any later version.
+
+   This program is distributed in the hope that it will be useful,
+   but WITHOUT ANY WARRANTY; without even the implied warranty of
+   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+   GNU General Public License for more details.
+
+   You should have received a copy of the GNU General Public License
+   along with this program.  If not, see <http://www.gnu.org/licenses/>.  */
+
+#include "defs.h"
+#include "block.h"
+#include "exceptions.h"
+#include "frame.h"
+#include "symtab.h"
+#include "python-internal.h"
+#include "objfiles.h"
+#include "value.h"
+
+typedef struct msympy_symbol_object {
+  PyObject_HEAD
+  /* The GDB minimal_symbol structure this object is wrapping.  */
+  struct minimal_symbol *minsym;
+  struct objfile *objfile;
+
+  struct type *type;
+  /* A symbol object is associated with an objfile, so keep track with
+     doubly-linked list, rooted in the objfile.  This lets us
+     invalidate the underlying struct minimal_symbol when the objfile is
+     deleted.  */
+  struct msympy_symbol_object *prev;
+  struct msympy_symbol_object *next;
+} minsym_object;
+
+/* Return the symbol that is wrapped by this symbol object.  */
+static struct minimal_symbol *
+minsym_object_to_minsym (PyObject *obj)
+{
+  if (! PyObject_TypeCheck (obj, &minsym_object_type))
+    return NULL;
+  return ((minsym_object *) obj)->minsym;
+}
+
+static struct objfile *
+minsym_object_to_objfile (PyObject *obj)
+{
+  if (! PyObject_TypeCheck (obj, &minsym_object_type))
+    return NULL;
+  return ((minsym_object *) obj)->objfile;
+}
+
+/* Require a valid symbol.  All access to minsym_object->symbol should be
+   gated by this call.  */
+#define MSYMPY_REQUIRE_VALID(minsym_obj, minsym)	\
+  do {							\
+    minsym = minsym_object_to_minsym (minsym_obj);	\
+    if (minsym == NULL)				\
+      {							\
+	PyErr_SetString (PyExc_RuntimeError,		\
+			 _("MinSymbol is invalid."));	\
+	return NULL;					\
+      }							\
+  } while (0)
+
+#define MSYMPY_REQUIRE_VALID_BOUND(minsym_obj, minsym, objfile)	\
+  do {								\
+    minsym = minsym_object_to_minsym (minsym_obj);		\
+    objfile = minsym_object_to_objfile (minsym_obj);		\
+    if (minsym == NULL || objfile == NULL)			\
+      {								\
+	PyErr_SetString (PyExc_RuntimeError,			\
+			 _("MinSymbol is invalid."));		\
+	return NULL;						\
+      }								\
+  } while (0)
+
+static PyObject *
+msympy_str (PyObject *self)
+{
+  PyObject *result;
+  struct minimal_symbol *minsym = NULL;
+
+  MSYMPY_REQUIRE_VALID (self, minsym);
+
+  result = PyString_FromString (MSYMBOL_PRINT_NAME (minsym));
+
+  return result;
+}
+
+static PyObject *
+msympy_get_name (PyObject *self, void *closure)
+{
+  struct minimal_symbol *minsym = NULL;
+
+  MSYMPY_REQUIRE_VALID (self, minsym);
+
+  return PyString_FromString (MSYMBOL_NATURAL_NAME (minsym));
+}
+
+static PyObject *
+msympy_get_file_name (PyObject *self, void *closure)
+{
+  struct minimal_symbol *minsym = NULL;
+
+  MSYMPY_REQUIRE_VALID (self, minsym);
+
+  return PyString_FromString (minsym->filename);
+}
+
+static PyObject *
+msympy_get_linkage_name (PyObject *self, void *closure)
+{
+  struct minimal_symbol *minsym = NULL;
+
+  MSYMPY_REQUIRE_VALID (self, minsym);
+
+  return PyString_FromString (MSYMBOL_LINKAGE_NAME (minsym));
+}
+
+static PyObject *
+msympy_get_print_name (PyObject *self, void *closure)
+{
+  struct minimal_symbol *minsym = NULL;
+
+  MSYMPY_REQUIRE_VALID (self, minsym);
+
+  return msympy_str (self);
+}
+
+static PyObject *
+msympy_get_section (PyObject *self, void *closure)
+{
+  struct minimal_symbol *minsym = NULL;
+  struct objfile *objfile = NULL;
+  struct obj_section *section;
+  const char *name;
+
+  MSYMPY_REQUIRE_VALID_BOUND (self, minsym, objfile);
+
+  section = MSYMBOL_OBJ_SECTION (objfile, minsym);
+  if (section) {
+    name = bfd_section_name (objfile->obfd, section->the_bfd_section);
+    if (name)
+      return PyString_FromString (name);
+  }
+
+  Py_RETURN_NONE;
+
+}
+
+static PyObject *
+msympy_is_valid (PyObject *self, PyObject *args)
+{
+  struct minimal_symbol *minsym = NULL;
+
+  minsym = minsym_object_to_minsym (self);
+  if (minsym == NULL)
+    Py_RETURN_FALSE;
+
+  Py_RETURN_TRUE;
+}
+
+/* Implementation of gdb.MinSymbol.value (self) -> gdb.Value.  Returns
+   the value of the symbol, or an error in various circumstances.  */
+
+static PyObject *
+msympy_value (PyObject *self, PyObject *args)
+{
+  minsym_object *minsym_obj = (minsym_object *)self;
+  struct minimal_symbol *minsym = NULL;
+  struct value *value = NULL;
+
+  if (!PyArg_ParseTuple (args, ""))
+    return NULL;
+
+  MSYMPY_REQUIRE_VALID (self, minsym);
+  TRY
+    {
+      value = value_from_ulongest(minsym_obj->type,
+				  MSYMBOL_VALUE_RAW_ADDRESS(minsym));
+      if (value)
+	set_value_address(value, MSYMBOL_VALUE_RAW_ADDRESS(minsym));
+    }
+  CATCH (except, RETURN_MASK_ALL)
+    {
+      GDB_PY_HANDLE_EXCEPTION (except);
+    }
+  END_CATCH
+
+  return value_to_value_object (value);
+}
+
+/* Given a symbol, and a minsym_object that has previously been
+   allocated and initialized, populate the minsym_object with the
+   struct minimal_symbol data.  Also, register the minsym_object life-cycle
+   with the life-cycle of the object file associated with this
+   symbol, if needed.  */
+static void
+set_symbol (minsym_object *obj, struct bound_minimal_symbol *bound)
+{
+  obj->minsym = bound->minsym;
+  obj->objfile = bound->objfile;
+  switch (obj->minsym->type) {
+  case mst_text:
+  case mst_solib_trampoline:
+  case mst_file_text:
+  case mst_text_gnu_ifunc:
+  case mst_slot_got_plt:
+    obj->type = builtin_type(python_gdbarch)->builtin_func_ptr;
+    break;
+
+  case mst_data:
+  case mst_abs:
+  case mst_bss:
+  case mst_file_data:
+  case mst_file_bss:
+    obj->type = builtin_type(python_gdbarch)->builtin_data_ptr;
+    break;
+
+  case mst_unknown:
+  default:
+    obj->type = builtin_type(python_gdbarch)->builtin_void;
+    break;
+  }
+
+  obj->prev = NULL;
+  obj->next = NULL;
+}
+
+static PyObject *
+bound_minsym_to_minsym_object (struct bound_minimal_symbol *bound)
+{
+  minsym_object *msym_obj;
+
+  msym_obj = PyObject_New (minsym_object, &minsym_object_type);
+  if (msym_obj)
+    set_symbol (msym_obj, bound);
+
+  return (PyObject *) msym_obj;
+}
+
+static void
+msympy_dealloc (PyObject *obj)
+{
+  minsym_object *msym_obj = (minsym_object *) obj;
+
+  if (msym_obj->prev)
+    msym_obj->prev->next = msym_obj->next;
+  if (msym_obj->next)
+    msym_obj->next->prev = msym_obj->prev;
+  msym_obj->minsym = NULL;
+  msym_obj->objfile = NULL;
+}
+
+/* Implementation of
+   gdb.lookup_minimal_symbol (name) -> symbol or None.  */
+
+PyObject *
+gdbpy_lookup_minimal_symbol (PyObject *self, PyObject *args, PyObject *kw)
+{
+  int domain = VAR_DOMAIN;
+  const char *name;
+  static char *keywords[] = { "name", NULL };
+  struct bound_minimal_symbol bound_minsym = {};
+  struct minimal_symbol *minsym = NULL;
+  PyObject *msym_obj = NULL;
+
+  if (!PyArg_ParseTupleAndKeywords (args, kw, "s|", keywords, &name))
+    return NULL;
+
+  TRY
+    {
+      bound_minsym = lookup_minimal_symbol (name, NULL, NULL);
+    }
+  CATCH (except, RETURN_MASK_ALL)
+    {
+      GDB_PY_HANDLE_EXCEPTION (except);
+    }
+  END_CATCH
+
+  if (bound_minsym.minsym)
+      msym_obj = bound_minsym_to_minsym_object (&bound_minsym);
+
+  if (msym_obj)
+    return msym_obj;
+
+  Py_RETURN_NONE;
+}
+
+int
+gdbpy_initialize_minsymbols (void)
+{
+  if (PyType_Ready (&minsym_object_type) < 0)
+    return -1;
+
+  if (PyModule_AddIntConstant (gdb_module, "MINSYMBOL_TYPE_UNKNOWN",
+			       mst_unknown) < 0
+  || PyModule_AddIntConstant (gdb_module, "MINSYMBOL_TYPE_TEXT", mst_text) < 0
+  || PyModule_AddIntConstant (gdb_module, "MINSYMBOL_TYPE_TEXT_GNU_IFUNC",
+			      mst_text_gnu_ifunc) < 0
+  || PyModule_AddIntConstant (gdb_module, "MINSYMBOL_TYPE_SLOT_GOT_PLT",
+			      mst_slot_got_plt) < 0
+  || PyModule_AddIntConstant (gdb_module, "MINSYMBOL_TYPE_DATA", mst_data) < 0
+  || PyModule_AddIntConstant (gdb_module, "MINSYMBOL_TYPE_BSS", mst_bss) < 0
+  || PyModule_AddIntConstant (gdb_module, "MINSYMBOL_TYPE_ABS", mst_abs) < 0
+  || PyModule_AddIntConstant (gdb_module, "MINSYMBOL_TYPE_SOLIB_TRAMPOLINE",
+			      mst_solib_trampoline) < 0
+  || PyModule_AddIntConstant (gdb_module, "MINSYMBOL_TYPE_FILE_TEXT",
+			      mst_file_text) < 0
+  || PyModule_AddIntConstant (gdb_module, "MINSYMBOL_TYPE_FILE_DATA",
+			      mst_file_data) < 0
+  || PyModule_AddIntConstant (gdb_module, "MINSYMBOL_TYPE_FILE_BSS",
+			      mst_file_bss) < 0)
+    return -1;
+
+  return gdb_pymodule_addobject (gdb_module, "MinSymbol",
+				 (PyObject *) &minsym_object_type);
+}
+
+\f
+
+static PyGetSetDef minsym_object_getset[] = {
+  { "name", msympy_get_name, NULL,
+    "Name of the symbol, as it appears in the source code.", NULL },
+  { "linkage_name", msympy_get_linkage_name, NULL,
+    "Name of the symbol, as used by the linker (i.e., may be mangled).",
+    NULL },
+  { "filename", msympy_get_file_name, NULL,
+    "Name of source file that contains this symbol. Only applies for mst_file_*.",
+    NULL },
+  { "print_name", msympy_get_print_name, NULL,
+    "Name of the symbol in a form suitable for output.\n\
+This is either name or linkage_name, depending on whether the user asked GDB\n\
+to display demangled or mangled names.", NULL },
+  { "section", msympy_get_section, NULL,
+    "Section that contains this symbol, if any", NULL, },
+  { NULL }  /* Sentinel */
+};
+
+static PyMethodDef minsym_object_methods[] = {
+  { "is_valid", msympy_is_valid, METH_NOARGS,
+    "is_valid () -> Boolean.\n\
+Return true if this symbol is valid, false if not." },
+  { "value", msympy_value, METH_VARARGS,
+    "value ([frame]) -> gdb.Value\n\
+Return the value of the symbol." },
+  {NULL}  /* Sentinel */
+};
+
+PyTypeObject minsym_object_type = {
+  PyVarObject_HEAD_INIT (NULL, 0)
+  "gdb.MinSymbol",		  /*tp_name*/
+  sizeof (minsym_object),	  /*tp_basicsize*/
+  0,				  /*tp_itemsize*/
+  msympy_dealloc,		  /*tp_dealloc*/
+  0,				  /*tp_print*/
+  0,				  /*tp_getattr*/
+  0,				  /*tp_setattr*/
+  0,				  /*tp_compare*/
+  0,				  /*tp_repr*/
+  0,				  /*tp_as_number*/
+  0,				  /*tp_as_sequence*/
+  0,				  /*tp_as_mapping*/
+  0,				  /*tp_hash */
+  0,				  /*tp_call*/
+  msympy_str,			  /*tp_str*/
+  0,				  /*tp_getattro*/
+  0,				  /*tp_setattro*/
+  0,				  /*tp_as_buffer*/
+  Py_TPFLAGS_DEFAULT,		  /*tp_flags*/
+  "GDB minimal symbol object",	  /*tp_doc */
+  0,				  /*tp_traverse */
+  0,				  /*tp_clear */
+  0,				  /*tp_richcompare */
+  0,				  /*tp_weaklistoffset */
+  0,				  /*tp_iter */
+  0,				  /*tp_iternext */
+  minsym_object_methods,	  /*tp_methods */
+  0,				  /*tp_members */
+  minsym_object_getset		  /*tp_getset */
+};
diff --git a/gdb/python/python-internal.h b/gdb/python/python-internal.h
index ee949b7..2fae31d 100644
--- a/gdb/python/python-internal.h
+++ b/gdb/python/python-internal.h
@@ -241,6 +241,8 @@ extern PyTypeObject block_object_type
     CPYCHECKER_TYPE_OBJECT_FOR_TYPEDEF("block_object");
 extern PyTypeObject symbol_object_type
     CPYCHECKER_TYPE_OBJECT_FOR_TYPEDEF ("symbol_object");
+extern PyTypeObject minsym_object_type;
+     CPYCHECKER_TYPE_OBJECT_FOR_TYPEDEF ("minsym_object");
 extern PyTypeObject event_object_type
     CPYCHECKER_TYPE_OBJECT_FOR_TYPEDEF ("event_object");
 extern PyTypeObject stop_event_object_type
@@ -362,6 +364,8 @@ PyObject *gdbpy_frame_stop_reason_string (PyObject *, PyObject *);
 PyObject *gdbpy_lookup_symbol (PyObject *self, PyObject *args, PyObject *kw);
 PyObject *gdbpy_lookup_global_symbol (PyObject *self, PyObject *args,
 				      PyObject *kw);
+PyObject *gdbpy_lookup_minimal_symbol (PyObject *self, PyObject *args,
+				       PyObject *kw);
 PyObject *gdbpy_newest_frame (PyObject *self, PyObject *args);
 PyObject *gdbpy_selected_frame (PyObject *self, PyObject *args);
 PyObject *gdbpy_block_for_pc (PyObject *self, PyObject *args);
@@ -436,6 +440,8 @@ int gdbpy_initialize_commands (void)
   CPYCHECKER_NEGATIVE_RESULT_SETS_EXCEPTION;
 int gdbpy_initialize_symbols (void)
   CPYCHECKER_NEGATIVE_RESULT_SETS_EXCEPTION;
+int gdbpy_initialize_minsymbols (void)
+  CPYCHECKER_NEGATIVE_RESULT_SETS_EXCEPTION;
 int gdbpy_initialize_symtabs (void)
   CPYCHECKER_NEGATIVE_RESULT_SETS_EXCEPTION;
 int gdbpy_initialize_blocks (void)
diff --git a/gdb/python/python.c b/gdb/python/python.c
index 6cbe5f0..30a86e1 100644
--- a/gdb/python/python.c
+++ b/gdb/python/python.c
@@ -1800,6 +1800,7 @@ message == an error message without a stack will be printed."),
       || gdbpy_initialize_frames () < 0
       || gdbpy_initialize_commands () < 0
       || gdbpy_initialize_symbols () < 0
+      || gdbpy_initialize_minsymbols () < 0
       || gdbpy_initialize_symtabs () < 0
       || gdbpy_initialize_blocks () < 0
       || gdbpy_initialize_functions () < 0
@@ -2025,6 +2026,10 @@ a boolean indicating if name is a field of the current implied argument\n\
     METH_VARARGS | METH_KEYWORDS,
     "lookup_global_symbol (name [, domain]) -> symbol\n\
 Return the symbol corresponding to the given name (or None)." },
+{ "lookup_minimal_symbol", (PyCFunction) gdbpy_lookup_minimal_symbol,
+    METH_VARARGS | METH_KEYWORDS,
+    "lookup_minimal_symbol (name) -> minsym\n\
+Return the symbol corresponding to the given name (or None)." },
 
   { "lookup_objfile", (PyCFunction) gdbpy_lookup_objfile,
     METH_VARARGS | METH_KEYWORDS,
-- 
2.1.4

^ permalink raw reply	[flat|nested] 17+ messages in thread

* [PATCH 1/7] check_types_equal: short circuit check if identical pointers are used
  2016-02-04 17:29 [PATCH 0/7] Python extension patchset jeffm
  2016-02-04 17:29 ` [PATCH 6/7] py-minsymbol: Add interface to access minimal_symbols jeffm
  2016-02-04 17:29 ` [PATCH 4/7] py-symbol: Require a frame for lookup_symbol only when necessary jeffm
@ 2016-02-04 17:29 ` jeffm
  2016-02-04 17:29 ` [PATCH 3/7] py-symbol: use Py_RETURN_NONE instead of open coding it jeffm
                   ` (3 subsequent siblings)
  6 siblings, 0 replies; 17+ messages in thread
From: jeffm @ 2016-02-04 17:29 UTC (permalink / raw)
  To: gdb-patches; +Cc: Jeff Mahoney

From: Jeff Mahoney <jeffm@suse.com>

If two types share identical pointers, we don't need to check typedefs
before comparing the result.
---
 gdb/gdbtypes.c | 3 +++
 1 file changed, 3 insertions(+)

diff --git a/gdb/gdbtypes.c b/gdb/gdbtypes.c
index b9850cf..1b6f276 100644
--- a/gdb/gdbtypes.c
+++ b/gdb/gdbtypes.c
@@ -3218,6 +3218,9 @@ static int
 check_types_equal (struct type *type1, struct type *type2,
 		   VEC (type_equality_entry_d) **worklist)
 {
+  if (type1 == type2)
+    return 1;
+
   type1 = check_typedef (type1);
   type2 = check_typedef (type2);
 
-- 
2.1.4

^ permalink raw reply	[flat|nested] 17+ messages in thread

* [PATCH 7/7] py-regcache: Add interface to regcache
  2016-02-04 17:29 [PATCH 0/7] Python extension patchset jeffm
                   ` (3 preceding siblings ...)
  2016-02-04 17:29 ` [PATCH 3/7] py-symbol: use Py_RETURN_NONE instead of open coding it jeffm
@ 2016-02-04 17:29 ` jeffm
  2016-02-04 17:43 ` [PATCH 2/7] py-value: properly handle unsigned and pointer types jeffm
  2016-02-04 17:43 ` [PATCH 5/7] py-symbol: export section name jeffm
  6 siblings, 0 replies; 17+ messages in thread
From: jeffm @ 2016-02-04 17:29 UTC (permalink / raw)
  To: gdb-patches; +Cc: Jeff Mahoney

From: Jeff Mahoney <jeffm@suse.com>

This patch adds new gdb.Register and gdb.RegCache objects to access
the register cache associated with a thread.  We can resolve regcache
objects via gdb.InferiorThread.
---
 gdb/Makefile.in              |   6 +
 gdb/python/py-infthread.c    |  31 ++++
 gdb/python/py-regcache.c     | 367 +++++++++++++++++++++++++++++++++++++++++++
 gdb/python/python-internal.h |   6 +
 gdb/python/python.c          |   3 +-
 5 files changed, 412 insertions(+), 1 deletion(-)
 create mode 100644 gdb/python/py-regcache.c

diff --git a/gdb/Makefile.in b/gdb/Makefile.in
index c2f7eef..e005485 100644
--- a/gdb/Makefile.in
+++ b/gdb/Makefile.in
@@ -406,6 +406,7 @@ SUBDIR_PYTHON_OBS = \
 	py-param.o \
 	py-prettyprint.o \
 	py-progspace.o \
+	py-regcache.o \
 	py-signalevent.o \
 	py-stopevent.o \
 	py-symbol.o \
@@ -447,6 +448,7 @@ SUBDIR_PYTHON_SRCS = \
 	python/py-param.c \
 	python/py-prettyprint.c \
 	python/py-progspace.c \
+	python/py-regcache.c \
 	python/py-signalevent.c \
 	python/py-stopevent.c \
 	python/py-symbol.c \
@@ -2661,6 +2663,10 @@ py-progspace.o: $(srcdir)/python/py-progspace.c
 	$(COMPILE) $(PYTHON_CFLAGS) $(srcdir)/python/py-progspace.c
 	$(POSTCOMPILE)
 
+py-regcache.o: $(srcdir)/python/py-regcache.c
+	$(COMPILE) $(PYTHON_CFLAGS) $(srcdir)/python/py-regcache.c
+	$(POSTCOMPILE)
+
 py-signalevent.o: $(srcdir)/python/py-signalevent.c
 	$(COMPILE) $(PYTHON_CFLAGS) $(srcdir)/python/py-signalevent.c
 	$(POSTCOMPILE)
diff --git a/gdb/python/py-infthread.c b/gdb/python/py-infthread.c
index e5db354..aa28ec6 100644
--- a/gdb/python/py-infthread.c
+++ b/gdb/python/py-infthread.c
@@ -47,6 +47,7 @@ create_thread_object (struct thread_info *tp)
 
   thread_obj->thread = tp;
   thread_obj->inf_obj = find_inferior_object (ptid_get_pid (tp->ptid));
+  thread_obj->regcache = NULL;
 
   return thread_obj;
 }
@@ -226,6 +227,34 @@ thpy_is_valid (PyObject *self, PyObject *args)
   Py_RETURN_TRUE;
 }
 
+static PyObject *
+thpy_get_regcache (PyObject *self, void *closure)
+{
+  thread_object *thread_obj = (thread_object *)self;
+  struct regcache *rc;
+  struct thread_info *tp;
+  TRY
+    {
+      THPY_REQUIRE_VALID(thread_obj);
+    }
+  CATCH (except, RETURN_MASK_ALL)
+    {
+      GDB_PY_HANDLE_EXCEPTION (except);
+    }
+  END_CATCH
+
+  if (thread_obj->regcache) {
+    Py_INCREF(thread_obj->regcache);
+    return thread_obj->regcache;
+  }
+
+  tp = thread_obj->thread;
+  rc = get_thread_regcache(tp->ptid);
+  thread_obj->regcache = regcache_to_regcache_object(rc);
+//  Py_INCREF(thread_obj->regcache);
+  return thread_obj->regcache;
+}
+
 /* Return a reference to a new Python object representing a ptid_t.
    The object is a tuple containing (pid, lwp, tid). */
 PyObject *
@@ -285,6 +314,8 @@ static PyGetSetDef thread_object_getset[] =
   { "num", thpy_get_num, NULL, "ID of the thread, as assigned by GDB.", NULL },
   { "ptid", thpy_get_ptid, NULL, "ID of the thread, as assigned by the OS.",
     NULL },
+  { "regcache", thpy_get_regcache, NULL, "Register cache for this thread.",
+    NULL },
 
   { NULL }
 };
diff --git a/gdb/python/py-regcache.c b/gdb/python/py-regcache.c
new file mode 100644
index 0000000..9447404
--- /dev/null
+++ b/gdb/python/py-regcache.c
@@ -0,0 +1,367 @@
+#include "defs.h"
+#include "python-internal.h"
+#include "regcache.h"
+
+extern PyTypeObject regcache_object_type;
+extern PyTypeObject register_object_type;
+
+typedef struct {
+  PyObject_HEAD
+  struct regcache *regcache;
+} regcache_object;
+
+typedef struct {
+  PyObject_HEAD
+  struct regcache *regcache;
+  const char *name;
+  int regnum;
+} register_object;
+
+/* Require a valid regcache.  All access to regcache_object->regcache should
+   be gated by this call. */
+#define RCPY_REQUIRE_VALID(regcache_obj, regcache)		\
+   do {								\
+     regcache = regcache_object_to_regcache (regcache_obj);	\
+     if (regcache == NULL)					\
+      {								\
+	PyErr_SetString (PyExc_RuntimeError,			\
+			 _("Regcache is invalid."));		\
+	return NULL;						\
+      }								\
+    } while (0)
+
+static void
+set_regcache(regcache_object *obj, struct regcache *rc)
+{
+  obj->regcache = rc;
+}
+
+PyObject *
+regcache_to_regcache_object (struct regcache *rc)
+{
+  regcache_object *regcache_obj;
+
+  regcache_obj = PyObject_New (regcache_object, &regcache_object_type);
+  if (regcache_obj)
+    set_regcache (regcache_obj, rc);
+  return (PyObject *) regcache_obj;
+}
+
+static regcache_object *
+regcache_object_to_regcache (PyObject *obj)
+{
+  if (! PyObject_TypeCheck (obj, &regcache_object_type))
+    return NULL;
+  return ((regcache_object *) obj);
+}
+
+#define RCPY_REG_REQUIRE_VALID(register_obj, reg, ret)		\
+  do {								\
+    reg = register_object_to_register(register_obj);		\
+    if (reg == NULL)						\
+      {								\
+	PyErr_SetString (PyExc_RuntimeError,			\
+			 _("Regcache is invalid."));		\
+	return ret;						\
+      }								\
+  } while(0)
+
+static void
+set_register(register_object *obj, struct regcache *rc,
+	     const char *name, int regnum)
+{
+  obj->regcache = rc;
+  obj->name = name;
+  obj->regnum = regnum;
+}
+
+static PyObject *
+register_to_register_object (struct regcache *rc, const char *name, int reg)
+{
+  register_object *register_obj;
+
+  register_obj = PyObject_New (register_object, &register_object_type);
+  if (register_obj)
+    set_register (register_obj, rc, name, reg);
+  return (PyObject *) register_obj;
+
+}
+
+static register_object *
+register_object_to_register (PyObject *obj)
+{
+  if (! PyObject_TypeCheck (obj, &register_object_type))
+    return NULL;
+  return ((register_object *) obj);
+}
+
+
+static PyObject *
+rcpy_get_registers (PyObject *self, void *closure)
+{
+  regcache_object *obj;
+  struct gdbarch *gdbarch;
+  int i, numregs;
+  PyObject *d;
+
+  RCPY_REQUIRE_VALID(self, obj);
+  gdbarch = get_regcache_arch(obj->regcache);
+  numregs = gdbarch_num_regs(gdbarch);
+
+  d = PyDict_New();
+  for (i = 0; i < numregs; i++)
+    {
+      struct register_object *robj;
+      const char *name = gdbarch_register_name(gdbarch, i);
+      PyObject *reg;
+
+      if (!name || !*name)
+	      continue;
+      reg = register_to_register_object (obj->regcache, name, i);
+      if (!reg) {
+	Py_DECREF(d);
+	return NULL;
+      }
+      if (PyDict_SetItemString(d, name, reg)) {
+	Py_DECREF(reg);
+	Py_DECREF(d);
+	return NULL;
+      }
+    }
+
+    return d;
+}
+
+static PyGetSetDef regcache_object_getset[] = {
+  { "registers", rcpy_get_registers, NULL, "Dictionary of registers.", NULL },
+  { NULL }  /* Sentinal */
+};
+
+PyTypeObject regcache_object_type = {
+  PyVarObject_HEAD_INIT (NULL, 0)
+  "gdb.RegCache",		  /*tp_name*/
+  sizeof(regcache_object),	  /*tp_basicsize*/
+  0,				  /*tp_itemsize*/
+  0,				  /*tp_delalloc*/
+  0,				  /*tp_print*/
+  0,				  /*tp_getattr*/
+  0,				  /*tp_setattr*/
+  0,				  /*tp_compare*/
+  0,				  /*tp_repr*/
+  0,				  /*tp_as_number*/
+  0,				  /*tp_as_sequence*/
+  0,				  /*tp_as_mapping*/
+  0,				  /*tp_hash */
+  0,				  /*tp_call*/
+  0,				  /*tp_str*/
+  0,				  /*tp_getattro*/
+  0,				  /*tp_setattro*/
+  0,				  /*tp_as_buffer*/
+  Py_TPFLAGS_DEFAULT,  		  /*tp_flags*/
+  "GDB regcache object",	  /* tp_doc */
+  0,				  /* tp_traverse */
+  0,				  /* tp_clear */
+  0,				  /* tp_richcompare */
+  0,				  /* tp_weaklistoffset */
+  0,				  /* tp_iter */
+  0,				  /* tp_iternext */
+  0,	  			  /* tp_methods */
+  0,				  /* tp_members */
+  regcache_object_getset,	  /* tp_getset */
+};
+
+static PyObject *
+register_get_name(PyObject *self, void *closure)
+{
+  register_object *obj;
+  RCPY_REG_REQUIRE_VALID(self, obj, NULL);
+
+  return PyString_FromString(obj->name);
+}
+
+static PyObject *
+register_get_value(PyObject *self, void *closure)
+{
+  register_object *obj;
+  struct value *value = NULL;
+
+  RCPY_REG_REQUIRE_VALID(self, obj, NULL);
+
+  TRY
+    {
+      /*
+       * We don't want raw read since that expects to
+       * read it from the core file
+       */
+      value = regcache_cooked_read_value(obj->regcache, obj->regnum);
+    }
+  CATCH (ex, RETURN_MASK_ERROR)
+    {
+      GDB_PY_HANDLE_EXCEPTION (ex);
+    }
+  END_CATCH
+
+  return value_to_value_object(value);
+}
+
+static const char *
+type_prefix (struct type *type)
+{
+  switch (TYPE_CODE(type))
+    {
+      case TYPE_CODE_UNION:
+	return "union ";
+      case TYPE_CODE_STRUCT:
+	return "struct ";
+      case TYPE_CODE_ENUM:
+	return "enum ";
+      }
+
+    return "";
+}
+
+static int
+register_set_value(PyObject *self, PyObject *value_obj, void *closure)
+{
+  register_object *obj;
+  struct type *type, *vtype = NULL;
+  struct value *value;
+  struct gdbarch *gdbarch;
+
+  RCPY_REG_REQUIRE_VALID(self, obj, -1);
+
+  value = value_object_to_value(value_obj);
+  if (value)
+    vtype = value_type(value);
+
+  gdbarch = get_regcache_arch(obj->regcache);
+  type = register_type (gdbarch, obj->regnum);
+
+  if (TYPE_CODE (type) == TYPE_CODE_PTR || is_integral_type (type))
+    {
+      unsigned long ul_value;
+      if (PyLong_Check(value_obj))
+	{
+	  ul_value = PyLong_AsUnsignedLong (value_obj);
+	  regcache_raw_supply (obj->regcache, obj->regnum, &ul_value);
+	}
+      else if (PyInt_Check (value_obj))
+	{
+	  ul_value = PyInt_AsUnsignedLongMask (value_obj);
+	  regcache_raw_supply (obj->regcache, obj->regnum, &ul_value);
+	}
+      else if (vtype && (TYPE_CODE(vtype) == TYPE_CODE_PTR ||
+			 is_integral_type (vtype)))
+	{
+	  regcache_raw_supply (obj->regcache, obj->regnum,
+			       value_contents (value));
+	}
+      else
+	{
+	  PyErr_SetString (PyExc_TypeError,
+			   "value must be pointer, int, long, or gdb.Value describing pointer or integral type");
+	  return -1;
+	}
+    }
+  else if (vtype && types_equal (type, vtype))
+    {
+      regcache_raw_supply (obj->regcache, obj->regnum, value_contents(value));
+    }
+  else
+    {
+      PyErr_Format (PyExc_TypeError,
+		    "value type for register must be gdb.Value describing `%s%s'",
+		    type_prefix (type), type_name_no_tag (type));
+      return -1;
+    }
+
+  return 0;
+}
+
+static PyObject *
+register_get_size(PyObject *self, void *closure)
+{
+  register_object *obj;
+  struct gdbarch *gdbarch;
+  RCPY_REG_REQUIRE_VALID(self, obj, NULL);
+  gdbarch = get_regcache_arch(obj->regcache);
+  return PyInt_FromLong(register_size(gdbarch, obj->regnum));
+}
+
+static PyObject *
+register_get_regnum(PyObject *self, void *closure)
+{
+  register_object *obj;
+  RCPY_REG_REQUIRE_VALID(self, obj, NULL);
+  return PyInt_FromLong(obj->regnum);
+}
+
+static PyObject *
+register_get_regtype(PyObject *self, void *closure)
+{
+  register_object *obj;
+  struct gdbarch *gdbarch;
+  struct type *type;
+  RCPY_REG_REQUIRE_VALID(self, obj, NULL);
+
+  gdbarch = get_regcache_arch(obj->regcache);
+  type = register_type(gdbarch, obj->regnum);
+
+  return type_to_type_object(type);
+}
+
+static PyGetSetDef register_object_getset[] = {
+  { "name", register_get_name, NULL, "Register name.", NULL },
+  { "value", register_get_value, register_set_value, "Register value.", NULL },
+  { "size", register_get_size, NULL, "Register size.", NULL },
+  { "regnum", register_get_regnum, NULL, "Register number.", NULL },
+  { "type", register_get_regtype, NULL, "Register type.", NULL },
+  { NULL }  /* Sentinal */
+};
+
+PyTypeObject register_object_type = {
+  PyVarObject_HEAD_INIT (NULL, 0)
+  "gdb.Register",		  /*tp_name*/
+  sizeof(register_object),	  /*tp_basicsize*/
+  0,				  /*tp_itemsize*/
+  0,				  /*tp_delalloc*/
+  0,				  /*tp_print*/
+  0,				  /*tp_getattr*/
+  0,				  /*tp_setattr*/
+  0,				  /*tp_compare*/
+  0,				  /*tp_repr*/
+  0,				  /*tp_as_number*/
+  0,				  /*tp_as_sequence*/
+  0,				  /*tp_as_mapping*/
+  0,				  /*tp_hash */
+  0,				  /*tp_call*/
+  0,				  /*tp_str*/
+  0,				  /*tp_getattro*/
+  0,				  /*tp_setattro*/
+  0,				  /*tp_as_buffer*/
+  Py_TPFLAGS_DEFAULT,		  /*tp_flags*/
+  "GDB register object",	  /* tp_doc */
+  0,				  /* tp_traverse */
+  0,				  /* tp_clear */
+  0,				  /* tp_richcompare */
+  0,				  /* tp_weaklistoffset */
+  0,				  /* tp_iter */
+  0,				  /* tp_iternext */
+  0,	  			  /* tp_methods */
+  0,				  /* tp_members */
+  register_object_getset,	  /* tp_getset */
+};
+
+int gdbpy_initialize_regcache (void)
+{
+    if (PyType_Ready (&register_object_type) < 0)
+      return -1;
+    if (PyType_Ready (&regcache_object_type) < 0)
+      return -1;
+
+    if (gdb_pymodule_addobject(gdb_module, "Register",
+			       (PyObject *)&register_object_type))
+      return -1;
+    return gdb_pymodule_addobject(gdb_module, "Regcache",
+				  (PyObject *)&regcache_object_type);
+}
diff --git a/gdb/python/python-internal.h b/gdb/python/python-internal.h
index 2fae31d..51f08ee 100644
--- a/gdb/python/python-internal.h
+++ b/gdb/python/python-internal.h
@@ -302,6 +302,9 @@ typedef struct
   /* The thread we represent.  */
   struct thread_info *thread;
 
+  /* Regcache */
+  PyObject *regcache;
+
   /* The Inferior object to which this thread belongs.  */
   PyObject *inf_obj;
 } thread_object;
@@ -504,6 +507,8 @@ int gdbpy_initialize_xmethods (void)
   CPYCHECKER_NEGATIVE_RESULT_SETS_EXCEPTION;
 int gdbpy_initialize_unwind (void)
   CPYCHECKER_NEGATIVE_RESULT_SETS_EXCEPTION;
+int gdbpy_initialize_regcache (void)
+  CPYCHECKER_NEGATIVE_RESULT_SETS_EXCEPTION;
 
 struct cleanup *make_cleanup_py_decref (PyObject *py);
 struct cleanup *make_cleanup_py_xdecref (PyObject *py);
@@ -600,4 +605,5 @@ struct varobj;
 struct varobj_iter *py_varobj_get_iterator (struct varobj *var,
 					    PyObject *printer);
 
+PyObject *regcache_to_regcache_object (struct regcache *rc);
 #endif /* GDB_PYTHON_INTERNAL_H */
diff --git a/gdb/python/python.c b/gdb/python/python.c
index 30a86e1..8218beb 100644
--- a/gdb/python/python.c
+++ b/gdb/python/python.c
@@ -1832,7 +1832,8 @@ message == an error message without a stack will be printed."),
       || gdbpy_initialize_clear_objfiles_event ()  < 0
       || gdbpy_initialize_arch () < 0
       || gdbpy_initialize_xmethods () < 0
-      || gdbpy_initialize_unwind () < 0)
+      || gdbpy_initialize_unwind () < 0
+      || gdbpy_initialize_regcache () < 0)
     goto fail;
 
   gdbpy_to_string_cst = PyString_FromString ("to_string");
-- 
2.1.4

^ permalink raw reply	[flat|nested] 17+ messages in thread

* [PATCH 3/7] py-symbol: use Py_RETURN_NONE instead of open coding it
  2016-02-04 17:29 [PATCH 0/7] Python extension patchset jeffm
                   ` (2 preceding siblings ...)
  2016-02-04 17:29 ` [PATCH 1/7] check_types_equal: short circuit check if identical pointers are used jeffm
@ 2016-02-04 17:29 ` jeffm
  2016-02-04 17:29 ` [PATCH 7/7] py-regcache: Add interface to regcache jeffm
                   ` (2 subsequent siblings)
  6 siblings, 0 replies; 17+ messages in thread
From: jeffm @ 2016-02-04 17:29 UTC (permalink / raw)
  To: gdb-patches; +Cc: Jeff Mahoney

From: Jeff Mahoney <jeffm@suse.com>

---
 gdb/python/py-symbol.c | 6 ++----
 1 file changed, 2 insertions(+), 4 deletions(-)

diff --git a/gdb/python/py-symbol.c b/gdb/python/py-symbol.c
index c1511b5..cbbc9e2 100644
--- a/gdb/python/py-symbol.c
+++ b/gdb/python/py-symbol.c
@@ -73,8 +73,7 @@ sympy_get_type (PyObject *self, void *closure)
 
   if (SYMBOL_TYPE (symbol) == NULL)
     {
-      Py_INCREF (Py_None);
-      return Py_None;
+      Py_RETURN_NONE;
     }
 
   return type_to_type_object (SYMBOL_TYPE (symbol));
@@ -471,8 +470,7 @@ gdbpy_lookup_global_symbol (PyObject *self, PyObject *args, PyObject *kw)
     }
   else
     {
-      sym_obj = Py_None;
-      Py_INCREF (Py_None);
+      Py_RETURN_NONE;
     }
 
   return sym_obj;
-- 
2.1.4

^ permalink raw reply	[flat|nested] 17+ messages in thread

* [PATCH 5/7] py-symbol: export section name
  2016-02-04 17:29 [PATCH 0/7] Python extension patchset jeffm
                   ` (5 preceding siblings ...)
  2016-02-04 17:43 ` [PATCH 2/7] py-value: properly handle unsigned and pointer types jeffm
@ 2016-02-04 17:43 ` jeffm
  2016-02-05 12:18   ` Phil Muldoon
  6 siblings, 1 reply; 17+ messages in thread
From: jeffm @ 2016-02-04 17:43 UTC (permalink / raw)
  To: gdb-patches; +Cc: Jeff Mahoney

From: Jeff Mahoney <jeffm@suse.com>

Some consumers of the symbol API need to know in what section a symbol is
located.  This exports the section name as a string.
---
 gdb/python/py-symbol.c | 23 +++++++++++++++++++++++
 1 file changed, 23 insertions(+)

diff --git a/gdb/python/py-symbol.c b/gdb/python/py-symbol.c
index c7f0ff8..aad2edc 100644
--- a/gdb/python/py-symbol.c
+++ b/gdb/python/py-symbol.c
@@ -238,6 +238,27 @@ sympy_is_valid (PyObject *self, PyObject *args)
   Py_RETURN_TRUE;
 }
 
+static PyObject *
+sympy_section (PyObject *self, void *closure)
+{
+  struct symbol *symbol = NULL;
+  PyObject *section_obj;
+  struct obj_section *section;
+  const char *name;
+
+  SYMPY_REQUIRE_VALID (self, symbol);
+
+  section = SYMBOL_OBJ_SECTION (symbol_objfile(symbol), symbol);
+  if (section) {
+    name = bfd_section_name (symbol_objfile(objfile)->obfd,
+			     section->the_bfd_section);
+    if (name)
+      return PyString_FromString (name);
+  }
+
+  Py_RETURN_NONE;
+}
+
 /* Implementation of gdb.Symbol.value (self[, frame]) -> gdb.Value.  Returns
    the value of the symbol, or an error in various circumstances.  */
 
@@ -590,6 +611,8 @@ to display demangled or mangled names.", NULL },
     "True if the symbol requires a frame for evaluation." },
   { "line", sympy_line, NULL,
     "The source line number at which the symbol was defined." },
+  { "section", sympy_section, NULL,
+    "Section of executable where symbol resides." },
   { NULL }  /* Sentinel */
 };
 
-- 
2.1.4

^ permalink raw reply	[flat|nested] 17+ messages in thread

* [PATCH 2/7] py-value: properly handle unsigned and pointer types
  2016-02-04 17:29 [PATCH 0/7] Python extension patchset jeffm
                   ` (4 preceding siblings ...)
  2016-02-04 17:29 ` [PATCH 7/7] py-regcache: Add interface to regcache jeffm
@ 2016-02-04 17:43 ` jeffm
  2016-02-05 12:12   ` Phil Muldoon
  2016-02-04 17:43 ` [PATCH 5/7] py-symbol: export section name jeffm
  6 siblings, 1 reply; 17+ messages in thread
From: jeffm @ 2016-02-04 17:43 UTC (permalink / raw)
  To: gdb-patches; +Cc: Jeff Mahoney

From: Jeff Mahoney <jeffm@suse.com>

GDB passes signed long values into python whether they're signed or
not.  This results in a situation where the caller needs to convert
it back to an unsigned value, which requires knowledge of the underlying
size of the value.  The information to do that is available in the API,
but it's unnecessary.  We know it's an unsigned value so pass it as
an unsigned value.
---
 gdb/python/py-value.c | 12 ++++++++++++
 1 file changed, 12 insertions(+)

diff --git a/gdb/python/py-value.c b/gdb/python/py-value.c
index 140aaf5..c557d95 100644
--- a/gdb/python/py-value.c
+++ b/gdb/python/py-value.c
@@ -1475,6 +1475,7 @@ valpy_int (PyObject *self)
 {
   struct value *value = ((value_object *) self)->value;
   struct type *type = value_type (value);
+  int is_unsigned = 0;
   LONGEST l = 0;
 
   TRY
@@ -1482,6 +1483,9 @@ valpy_int (PyObject *self)
       if (!is_integral_type (type))
 	error (_("Cannot convert value to int."));
 
+      if (TYPE_CODE (type) == TYPE_CODE_PTR ||
+	  TYPE_UNSIGNED(type))
+	is_unsigned = 1;
       l = value_as_long (value);
     }
   CATCH (except, RETURN_MASK_ALL)
@@ -1490,6 +1494,8 @@ valpy_int (PyObject *self)
     }
   END_CATCH
 
+  if (is_unsigned)
+    return gdb_py_object_from_ulongest ((ULONGEST)l);
   return gdb_py_object_from_longest (l);
 }
 #endif
@@ -1500,6 +1506,7 @@ valpy_long (PyObject *self)
 {
   struct value *value = ((value_object *) self)->value;
   struct type *type = value_type (value);
+  int is_unsigned = 0;
   LONGEST l = 0;
 
   TRY
@@ -1510,6 +1517,9 @@ valpy_long (PyObject *self)
 	  && TYPE_CODE (type) != TYPE_CODE_PTR)
 	error (_("Cannot convert value to long."));
 
+      if (TYPE_CODE (type) == TYPE_CODE_PTR ||
+	  TYPE_UNSIGNED(type))
+	is_unsigned = 1;
       l = value_as_long (value);
     }
   CATCH (except, RETURN_MASK_ALL)
@@ -1518,6 +1528,8 @@ valpy_long (PyObject *self)
     }
   END_CATCH
 
+  if (is_unsigned)
+    return gdb_py_long_from_ulongest ((ULONGEST)l);
   return gdb_py_long_from_longest (l);
 }
 
-- 
2.1.4

^ permalink raw reply	[flat|nested] 17+ messages in thread

* Re: [PATCH 2/7] py-value: properly handle unsigned and pointer types
  2016-02-04 17:43 ` [PATCH 2/7] py-value: properly handle unsigned and pointer types jeffm
@ 2016-02-05 12:12   ` Phil Muldoon
  2016-02-05 12:29     ` Phil Muldoon
  0 siblings, 1 reply; 17+ messages in thread
From: Phil Muldoon @ 2016-02-05 12:12 UTC (permalink / raw)
  To: jeffm, gdb-patches

On 04/02/16 17:29, jeffm@suse.com wrote:
> From: Jeff Mahoney <jeffm@suse.com>
>
> GDB passes signed long values into python whether they're signed or
> not.  This results in a situation where the caller needs to convert
> it back to an unsigned value, which requires knowledge of the underlying
> size of the value.  The information to do that is available in the API,
> but it's unnecessary.  We know it's an unsigned value so pass it as
> an unsigned value.
> ---
>  gdb/python/py-value.c | 12 ++++++++++++
>  1 file changed, 12 insertions(+)
>
> diff --git a/gdb/python/py-value.c b/gdb/python/py-value.c
> index 140aaf5..c557d95 100644
> --- a/gdb/python/py-value.c
> +++ b/gdb/python/py-value.c
> @@ -1475,6 +1475,7 @@ valpy_int (PyObject *self)
>  {
>    struct value *value = ((value_object *) self)->value;
>    struct type *type = value_type (value);
> +  int is_unsigned = 0;
>    LONGEST l 
>>
>> jeff
>>
> = 0;
>  
>    TRY
> @@ -1482,6 +1483,9 @@ valpy_int (PyObject *self)
>        if (!is_integral_type (type))
>  	error (_("Cannot convert value to int."));
>  
> +      if (TYPE_CODE (type) == TYPE_CODE_PTR ||
> +	  TYPE_UNSIGNED(type))
Nit, space after the macro/function name and before (.
> +	is_unsigned = 1;
>        l = value_as_long (value);
>      }
>    CATCH (exc
>>
>> jeff
>>
> ept, RETURN_MASK_ALL)
> @@ -1490,6 +1494,8 @@ valpy_int (PyObject *self)
>      }
>    END_CATCH
>  
> +  if (is_unsigned)
> +    return gdb_py_object_from_ulongest ((ULONGEST)l);
>    return gdb_py_object_from_longest (l);
>  }
>  #endif
> @@ -1500,6 +1506,7 @@ valpy_long (PyObject *self)
>  {
>    struct value *value = ((value_object *) self)->value;
>    struct type *type = value_type (value);
> +  int is_unsigned = 0;
>    LONGEST l = 0;
>  
>    TRY
> @@ -1510,6 +1517,9 @@ valpy_long (PyObject *self)
>  	  && TYPE_CODE (type) != TYPE_CODE_PTR)
>  	error (_("Cannot convert value to long."));
>  
> +      if (TYPE_CODE (type) == TYPE_CODE_PTR ||
> +	  TYPE_UNSIGNED(type))
Nit, space after the macro/function name and before (.
> +	is_unsigned = 1;
>        l = value_as_long (value);
>      }
>    CATCH (except, RETURN_MASK_ALL)
> @@ -1518,6 +1528,8 @@ valpy_long (PyObject *self)
>      }
>    END_CATCH
>  
> +  if (is_unsigned)
> +    return gdb_py_long_from_ulongest ((ULONGEST)l);
>    return gdb_py_long_from_longest (l);
>  }
>  

Thanks. This needs tests and documentation changes for the changes in functionality.

Cheers

Phil

^ permalink raw reply	[flat|nested] 17+ messages in thread

* Re: [PATCH 4/7] py-symbol: Require a frame for lookup_symbol only when necessary
  2016-02-04 17:29 ` [PATCH 4/7] py-symbol: Require a frame for lookup_symbol only when necessary jeffm
@ 2016-02-05 12:17   ` Phil Muldoon
  2016-02-05 16:08     ` Jeff Mahoney
  2016-02-05 16:35   ` Phil Muldoon
  1 sibling, 1 reply; 17+ messages in thread
From: Phil Muldoon @ 2016-02-05 12:17 UTC (permalink / raw)
  To: jeffm, gdb-patches

On 04/02/16 17:29, jeffm@suse.com wrote:
> From: Jeff Mahoney <jeffm@suse.com> > > gdbpy_lookup_symbol requires a frame prior to doing the symbol lookup but > a frame isn't necessary for many symbol types.  Calling > symbol_read_needs_frame will tell us if it's necessary but we need to > have already looked up the symbol to use it.  This patch puts the > lookup first and then only resolves the frame if one is required. > > This allows us to lookup static symbols directly from python rather > than using gdb.eval_and_parse.

Please add documentation and further tests for new functionality.

> --- >  gdb/python/py-symbol.c | 31 +++++++++++++++++-------------- >  1 file changed, 17 insertions(+), 14 deletions(-) > > diff --git a/gdb/python/py-symbol.c b/gdb/python/py-symbol.c > index cbbc9e2..c7f0ff8 100644 > --- a/gdb/python/py-symbol.c > +++ b/gdb/python/py-symbol.c > @@ -382,14 +382,28 @@ gdbpy_lookup_symbol (PyObject *self, PyObject *args, PyObject *kw) >  >    if (block_obj) >      block = block_object_to_block (block_obj); > -  else > + > +  TRY > +    { > +      symbol = lookup_symbol (name, block, (domain_enum) domain, > +                  &is_a_field_of_this).symbol; > +    } > +  CATCH (except, RETURN_MASK_ALL) > +    { > +      GDB_PY_HANDLE_EXCEPTION (except); > +    } > +  END_CATCH > + > +  if (symbol && !block) >      { >        struct frame_info *selected_frame; >  >        TRY >      { > -      selected_frame = get_selected_frame (_("No frame selected.")); > -      block = get_frame_block (selected_frame, NULL); > +      if
(symbol_read_needs_frame(symbol)) {

Formatting nit, space after function name and before (.

> +        selected_frame = get_selected_frame (_("No frame selected.")); > +        block = get_frame_block (selected_frame, NULL); > +      } >      } >        CATCH (except, RETURN_MASK_ALL) >      { > @@ -398,17 +412,6 @@ gdbpy_lookup_symbol (PyObject *self, PyObject *args, PyObject *kw) >        END_CATCH >      }

My only concern here is (and the context is not meaningful enough to
see), is that you've removed an "else" above which is an unconditional
branch, and replaced it with an IF instead. What happens when both IFs
can fail?

Cheers

Phil



^ permalink raw reply	[flat|nested] 17+ messages in thread

* Re: [PATCH 5/7] py-symbol: export section name
  2016-02-04 17:43 ` [PATCH 5/7] py-symbol: export section name jeffm
@ 2016-02-05 12:18   ` Phil Muldoon
  0 siblings, 0 replies; 17+ messages in thread
From: Phil Muldoon @ 2016-02-05 12:18 UTC (permalink / raw)
  To: jeffm, gdb-patches

On 04/02/16 17:29, jeffm@suse.com wrote:
> From: Jeff Mahoney <jeffm@suse.com>
>
> Some consumers of the symbol API need to know in what section a symbol is
> located.  This exports the section name as a string.
> ---
>  gdb/python/py-symbol.c | 23 +++++++++++++++++++++++
>  1 file changed, 23 insertions(+)
>
> diff --git a/gdb/python/py-symbol.c b/gdb/python/py-symbol.c
> index c7f0ff8..aad2edc 100644
> --- a/gdb/python/py-symbol.c
> +++ b/gdb/python/py-symbol.c
> @@ -238,6 +238,27 @@ sympy_is_valid (PyObject *self, PyObject *args)
>    Py_RETURN_TRUE;
>  }
>  
> +static PyObject *
> +sympy_section (PyObject *self, void *closure)
> +{
> +  struct symbol *symbol = NULL;
> +  PyObject *section_obj;
> +  struct obj_section *section;
> +  const char *name;
> +
> +  SYMPY_REQUIRE_VALID (self, symbol);
> +
> +  section = SYMBOL_OBJ_SECTION (symbol_objfile(symbol), symbol);
> +  if (section) {
> +    name = bfd_section_name (symbol_objfile(objfile)->obfd,
> +			     section->the_bfd_section);
> +    if (name)
> +      return PyString_FromString (name);
> +  }
> +
> +  Py_RETURN_NONE;
> +}
> +
>  /* Implementation of gdb.Symbol.value (self[, frame]) -> gdb.Value.  Returns
>     the value of the symbol, or an error in various circumstances.  */
>  
> @@ -590,6 +611,8 @@ to display demangled or mangled names.", NULL },
>      "True if the symbol requires a frame for evaluation." },
>    { "line", sympy_line, NULL,
>      "The source line number at which the symbol was defined." },
> +  { "section", sympy_section, NULL,
> +    "Section of executable where symbol resides." },
>    { NULL }  /* Sentinel */
>  };
>  
This looks fine, but it needs a documentation entry and tests.

Cheers

Phil

^ permalink raw reply	[flat|nested] 17+ messages in thread

* Re: [PATCH 6/7] py-minsymbol: Add interface to access minimal_symbols
  2016-02-04 17:29 ` [PATCH 6/7] py-minsymbol: Add interface to access minimal_symbols jeffm
@ 2016-02-05 12:25   ` Phil Muldoon
  2016-02-05 16:43   ` Phil Muldoon
  1 sibling, 0 replies; 17+ messages in thread
From: Phil Muldoon @ 2016-02-05 12:25 UTC (permalink / raw)
  To: jeffm, gdb-patches

On 04/02/16 17:29, jeffm@suse.com wrote:
> From: Jeff Mahoney <jeffm@suse.com> > > This patch adds a new gdb.MinSymbol object to export the minimal_symbol > interface.  These objects can be resolved using a new > gdb.lookup_minimal_symbol call. > --- >  gdb/Makefile.in              |   6 + >  gdb/python/py-minsymbol.c    | 390 +++++++++++++++++++++++++++++++++++++++++++ >  gdb/python/python-internal.h |   6 + >  gdb/python/python.c          |   5 + >  4 files changed, 407 insertions(+) >  create mode 100644 gdb/python/py-minsymbol.c > > diff --git a/gdb/Makefile.in b/gdb/Makefile.in > index 3eadbbc..c2f7eef 100644 > --- a/gdb/Makefile.in > +++ b/gdb/Makefile.in > @@ -400,6 +400,7 @@ SUBDIR_PYTHON_OBS = \ >      py-infthread.o \ >      py-lazy-string.o \ >      py-linetable.o \ > +    py-minsymbol.o \ >      py-newobjfileevent.o \ >      py-objfile.o \ >      py-param.o \ > @@ -440,6 +441,7 @@ SUBDIR_PYTHON_SRCS = \ >      python/py-infthread.c \ >      python/py-lazy-string.c \ >      python/py-linetable.c \ > +    python/py-minsymbol.c \ >     
python/py-newobjfileevent.c \ >      python/py-objfile.c \ >      python/py-param.c \ > @@ -2635,6 +2637,10 @@ py-linetable.o: $(srcdir)/python/py-linetable.c >      $(COMPILE) $(PYTHON_CFLAGS) $(srcdir)/python/py-linetable.c >      $(POSTCOMPILE) >  > +py-minsymbol.o: $(srcdir)/python/py-minsymbol.c > +    $(COMPILE) $(PYTHON_CFLAGS) $(srcdir)/python/py-minsymbol.c > +    $(POSTCOMPILE) > + >  py-newobjfileevent.o: $(srcdir)/python/py-newobjfileevent.c >      $(COMPILE) $(PYTHON_CFLAGS) $(srcdir)/python/py-newobjfileevent.c >      $(POSTCOMPILE) > diff --git a/gdb/python/py-minsymbol.c b/gdb/python/py-minsymbol.c > new file mode 100644 > index 0000000..d8b56bc > --- /dev/null > +++ b/gdb/python/py-minsymbol.c > @@ -0,0 +1,390 @@ > +/* Python interface to minsymbols. > + > +   Copyright (C) 2008-2013 Free Software Foundation, Inc.

Wrong copyright date.

> + > +   This file is part of GDB. > + > +   This program is free software; you can redistribute it and/or modify > +   it under the terms of the GNU General Public License as published by > +   the Free Software Foundation; either version 3 of the License, or > +   (at your option) any later version. > + > +   This program is distributed in the hope that it will be useful, > +   but WITHOUT ANY WARRANTY; without even the implied warranty of > +   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the > +   GNU General Public License for more details. > + > +   You should have received a copy of the GNU General Public License > +   along with this program.  If not, see <http://www.gnu.org/licenses/>.  */ > + > +#include "defs.h" > +#include "block.h" > +#include "exceptions.h" > +#include "frame.h" > +#include "symtab.h" > +#include "python-internal.h" > +#include "objfiles.h" > +#include "value.h" > + > +typedef struct msympy_symbol_object { > +  PyObject_HEAD > +  /*
The GDB minimal_symbol structure this object is wrapping.  */ > +  struct minimal_symbol *minsym; > +  struct objfile *objfile; > + > +  struct type *type; > +  /* A symbol object is associated with an objfile, so keep track with > +     doubly-linked list, rooted in the objfile.  This lets us > +     invalidate the underlying struct minimal_symbol when the objfile is > +     deleted.  */ > +  struct msympy_symbol_object *prev; > +  struct msympy_symbol_object *next; > +} minsym_object;

Can you please document all elements in the struct.

> +/* Return the symbol that is wrapped by this symbol object.  */ > +static struct minimal_symbol * > +minsym_object_to_minsym (PyObject *obj) > +{ > +  if (! PyObject_TypeCheck (obj, &minsym_object_type)) > +    return NULL; > +  return ((minsym_object *) obj)->minsym; > +} > + > +static struct objfile * > +minsym_object_to_objfile (PyObject *obj) > +{ > +  if (! PyObject_TypeCheck (obj, &minsym_object_type)) > +    return NULL; > +  return ((minsym_object *) obj)->objfile; > +} > + > +/* Require a valid symbol.  All access to minsym_object->symbol should be > +   gated by this call.  */ > +#define MSYMPY_REQUIRE_VALID(minsym_obj, minsym)    \ > +  do {                            \ > +    minsym = minsym_object_to_minsym (minsym_obj);    \ > +    if (minsym == NULL)                \ > +      {                            \ > +    PyErr_SetString (PyExc_RuntimeError,        \ > +             _("MinSymbol is invalid."));    \ > +    return NULL;                    \ > +      }                            \ > +  } while (0) > + > +#define
MSYMPY_REQUIRE_VALID_BOUND(minsym_obj, minsym, objfile)    \ > +  do {                                \ > +    minsym = minsym_object_to_minsym (minsym_obj);        \ > +    objfile = minsym_object_to_objfile (minsym_obj);        \ > +    if (minsym == NULL || objfile == NULL)            \ > +      {                                \ > +    PyErr_SetString (PyExc_RuntimeError,            \ > +             _("MinSymbol is invalid."));        \ > +    return NULL;                        \ > +      }                                \ > +  } while (0) > + > +static PyObject * > +msympy_str (PyObject *self) > +{ > +  PyObject *result; > +  struct minimal_symbol *minsym = NULL; > + > +  MSYMPY_REQUIRE_VALID (self, minsym); > + > +  result = PyString_FromString (MSYMBOL_PRINT_NAME (minsym)); > + > +  return result; > +} > + > +static PyObject * > +msympy_get_name (PyObject *self, void *closure) > +{ > +  struct minimal_symbol *minsym = NULL; > + > +  MSYMPY_REQUIRE_VALID (self,
minsym); > + > +  return PyString_FromString (MSYMBOL_NATURAL_NAME (minsym)); > +} > + > +static PyObject * > +msympy_get_file_name (PyObject *self, void *closure) > +{ > +  struct minimal_symbol *minsym = NULL; > + > +  MSYMPY_REQUIRE_VALID (self, minsym); > + > +  return PyString_FromString (minsym->filename); > +} > + > +static PyObject * > +msympy_get_linkage_name (PyObject *self, void *closure) > +{ > +  struct minimal_symbol *minsym = NULL; > + > +  MSYMPY_REQUIRE_VALID (self, minsym); > + > +  return PyString_FromString (MSYMBOL_LINKAGE_NAME (minsym)); > +} > + > +static PyObject * > +msympy_get_print_name (PyObject *self, void *closure) > +{ > +  struct minimal_symbol *minsym = NULL; > + > +  MSYMPY_REQUIRE_VALID (self, minsym); > + > +  return msympy_str (self); > +} > + > +static PyObject * > +msympy_get_section (PyObject *self, void *closure) > +{ > +  struct minimal_symbol *minsym = NULL; > +  struct objfile *objfile = NULL; > +  struct obj_section *section; > + 
const char *name; > + > +  MSYMPY_REQUIRE_VALID_BOUND (self, minsym, objfile); > + > +  section = MSYMBOL_OBJ_SECTION (objfile, minsym); > +  if (section) {

Newline before {.

> +    name = bfd_section_name (objfile->obfd, section->the_bfd_section); > +    if (name) > +      return PyString_FromString (name); > +  } > + > +  Py_RETURN_NONE; > + > +} > + > +static PyObject * > +msympy_is_valid (PyObject *self, PyObject *args) > +{ > +  struct minimal_symbol *minsym = NULL; > + > +  minsym = minsym_object_to_minsym (self); > +  if (minsym == NULL) > +    Py_RETURN_FALSE; > + > +  Py_RETURN_TRUE; > +} > + > +/* Implementation of gdb.MinSymbol.value (self) -> gdb.Value.  Returns > +   the value of the symbol, or an error in various circumstances.  */ > + > +static PyObject * > +msympy_value (PyObject *self, PyObject *args) > +{ > +  minsym_object *minsym_obj = (minsym_object *)self; > +  struct minimal_symbol *minsym = NULL; > +  struct value *value = NULL; > + > +  if (!PyArg_ParseTuple (args, "")) > +    return NULL; > + > +  MSYMPY_REQUIRE_VALID (self, minsym); > +  TRY > +    { > +      value = value_from_ulongest(minsym_obj->type, > +                  MSYMBOL_VALUE_RAW_ADDRESS(minsym));

Spaces in function name and (. This an others.

> +      if (value) > +    set_value_address(value, MSYMBOL_VALUE_RAW_ADDRESS(minsym)); > +    }

Ditto x 2.

> +  CATCH (except, RETURN_MASK_ALL) > +    { > +      GDB_PY_HANDLE_EXCEPTION (except); > +    } > +  END_CATCH > + > +  return value_to_value_object (value); > +} > + > +/* Given a symbol, and a minsym_object that has previously been > +   allocated and initialized, populate the minsym_object with the > +   struct minimal_symbol data.  Also, register the minsym_object life-cycle > +   with the life-cycle of the object file associated with this > +   symbol, if needed.  */ > +static void > +set_symbol (minsym_object *obj, struct bound_minimal_symbol *bound) > +{ > +  obj->minsym = bound->minsym; > +  obj->objfile = bound->objfile; > +  switch (obj->minsym->type) { > +  case mst_text: > +  case mst_solib_trampoline: > +  case mst_file_text: > +  case mst_text_gnu_ifunc: > +  case mst_slot_got_plt: > +    obj->type = builtin_type(python_gdbarch)->builtin_func_ptr; > +    break; > +

Ditto.

> +  case mst_data: > +  case mst_abs: > +  case mst_bss: > +  case mst_file_data: > +  case mst_file_bss: > +    obj->type = builtin_type(python_gdbarch)->builtin_data_ptr; > +    break; > +

Ditto.

> +  case mst_unknown: > +  default: > +    obj->type = builtin_type(python_gdbarch)->builtin_void; > +    break; > +  } > +

Ditto.
> +  obj->prev = NULL; > +  obj->next = NULL; > +} > + > +static PyObject * > +bound_minsym_to_minsym_object (struct bound_minimal_symbol *bound) > +{ > +  minsym_object *msym_obj; > + > +  msym_obj = PyObject_New (minsym_object, &minsym_object_type); > +  if (msym_obj) > +    set_symbol (msym_obj, bound); > + > +  return (PyObject *) msym_obj; > +} > + > +static void > +msympy_dealloc (PyObject *obj) > +{ > +  minsym_object *msym_obj = (minsym_object *) obj; > + > +  if (msym_obj->prev) > +    msym_obj->prev->next = msym_obj->next; > +  if (msym_obj->next) > +    msym_obj->next->prev = msym_obj->prev; > +  msym_obj->minsym = NULL; > +  msym_obj->objfile = NULL; > +} > + > +/* Implementation of > +   gdb.lookup_minimal_symbol (name) -> symbol or None.  */ > + > +PyObject * > +gdbpy_lookup_minimal_symbol (PyObject *self, PyObject *args, PyObject *kw) > +{ > +  int domain = VAR_DOMAIN; > +  const char *name; > +  static char *keywords[] = { "name", NULL }; > +  struct bound_minimal_symbol
bound_minsym = {}; > +  struct minimal_symbol *minsym = NULL; > +  PyObject *msym_obj = NULL; > + > +  if (!PyArg_ParseTupleAndKeywords (args, kw, "s|", keywords, &name)) > +    return NULL; > + > +  TRY > +    { > +      bound_minsym = lookup_minimal_symbol (name, NULL, NULL); > +    } > +  CATCH (except, RETURN_MASK_ALL) > +    { > +      GDB_PY_HANDLE_EXCEPTION (except); > +    } > +  END_CATCH > + > +  if (bound_minsym.minsym) > +      msym_obj = bound_minsym_to_minsym_object (&bound_minsym); > + > +  if (msym_obj) > +    return msym_obj; > + > +  Py_RETURN_NONE; > +} > + > +int > +gdbpy_initialize_minsymbols (void) > +{ > +  if (PyType_Ready (&minsym_object_type) < 0) > +    return -1; > + > +  if (PyModule_AddIntConstant (gdb_module, "MINSYMBOL_TYPE_UNKNOWN", > +                   mst_unknown) < 0 > +  || PyModule_AddIntConstant (gdb_module, "MINSYMBOL_TYPE_TEXT", mst_text) < 0 > +  || PyModule_AddIntConstant (gdb_module, "MINSYMBOL_TYPE_TEXT_GNU_IFUNC", > +           
      mst_text_gnu_ifunc) < 0 > +  || PyModule_AddIntConstant (gdb_module, "MINSYMBOL_TYPE_SLOT_GOT_PLT", > +                  mst_slot_got_plt) < 0 > +  || PyModule_AddIntConstant (gdb_module, "MINSYMBOL_TYPE_DATA", mst_data) < 0 > +  || PyModule_AddIntConstant (gdb_module, "MINSYMBOL_TYPE_BSS", mst_bss) < 0 > +  || PyModule_AddIntConstant (gdb_module, "MINSYMBOL_TYPE_ABS", mst_abs) < 0 > +  || PyModule_AddIntConstant (gdb_module, "MINSYMBOL_TYPE_SOLIB_TRAMPOLINE", > +                  mst_solib_trampoline) < 0 > +  || PyModule_AddIntConstant (gdb_module, "MINSYMBOL_TYPE_FILE_TEXT", > +                  mst_file_text) < 0 > +  || PyModule_AddIntConstant (gdb_module, "MINSYMBOL_TYPE_FILE_DATA", > +                  mst_file_data) < 0 > +  || PyModule_AddIntConstant (gdb_module, "MINSYMBOL_TYPE_FILE_BSS", > +                  mst_file_bss) < 0) > +    return -1; > + > +  return gdb_pymodule_addobject (gdb_module, "MinSymbol", > +                 (PyObject *)
&minsym_object_type); > +} > + > +\f > + > +static PyGetSetDef minsym_object_getset[] = { > +  { "name", msympy_get_name, NULL, > +    "Name of the symbol, as it appears in the source code.", NULL }, > +  { "linkage_name", msympy_get_linkage_name, NULL, > +    "Name of the symbol, as used by the linker (i.e., may be mangled).", > +    NULL }, > +  { "filename", msympy_get_file_name, NULL, > +    "Name of source file that contains this symbol. Only applies for mst_file_*.", > +    NULL }, > +  { "print_name", msympy_get_print_name, NULL, > +    "Name of the symbol in a form suitable for output.\n\ > +This is either name or linkage_name, depending on whether the user asked GDB\n\ > +to display demangled or mangled names.", NULL }, > +  { "section", msympy_get_section, NULL, > +    "Section that contains this symbol, if any", NULL, }, > +  { NULL }  /* Sentinel */ > +}; > + > +static PyMethodDef minsym_object_methods[] = { > +  { "is_valid", msympy_is_valid, METH_NOARGS, > +   
"is_valid () -> Boolean.\n\ > +Return true if this symbol is valid, false if not." }, > +  { "value", msympy_value, METH_VARARGS, > +    "value ([frame]) -> gdb.Value\n\ > +Return the value of the symbol." }, > +  {NULL}  /* Sentinel */ > +}; > + > +PyTypeObject minsym_object_type = { > +  PyVarObject_HEAD_INIT (NULL, 0) > +  "gdb.MinSymbol",          /*tp_name*/ > +  sizeof (minsym_object),      /*tp_basicsize*/ > +  0,                  /*tp_itemsize*/ > +  msympy_dealloc,          /*tp_dealloc*/ > +  0,                  /*tp_print*/ > +  0,                  /*tp_getattr*/ > +  0,                  /*tp_setattr*/ > +  0,                  /*tp_compare*/ > +  0,                  /*tp_repr*/ > +  0,                  /*tp_as_number*/ > +  0,                  /*tp_as_sequence*/ > +  0,                  /*tp_as_mapping*/ > +  0,                  /*tp_hash */ > +  0,                  /*tp_call*/ > +  msympy_str,              /*tp_str*/ > +  0,                  /*tp_getattro*/ > + 
0,                  /*tp_setattro*/ > +  0,                  /*tp_as_buffer*/ > +  Py_TPFLAGS_DEFAULT,          /*tp_flags*/ > +  "GDB minimal symbol object",      /*tp_doc */ > +  0,                  /*tp_traverse */ > +  0,                  /*tp_clear */ > +  0,                  /*tp_richcompare */ > +  0,                  /*tp_weaklistoffset */ > +  0,                  /*tp_iter */ > +  0,                  /*tp_iternext */ > +  minsym_object_methods,      /*tp_methods */ > +  0,                  /*tp_members */ > +  minsym_object_getset          /*tp_getset */ > +}; > diff --git a/gdb/python/python-internal.h b/gdb/python/python-internal.h > index ee949b7..2fae31d 100644 > --- a/gdb/python/python-internal.h > +++ b/gdb/python/python-internal.h > @@ -241,6 +241,8 @@ extern PyTypeObject block_object_type >      CPYCHECKER_TYPE_OBJECT_FOR_TYPEDEF("block_object"); >  extern PyTypeObject symbol_object_type >      CPYCHECKER_TYPE_OBJECT_FOR_TYPEDEF ("symbol_object"); > +extern
PyTypeObject minsym_object_type; > +     CPYCHECKER_TYPE_OBJECT_FOR_TYPEDEF ("minsym_object"); >  extern PyTypeObject event_object_type >      CPYCHECKER_TYPE_OBJECT_FOR_TYPEDEF ("event_object"); >  extern PyTypeObject stop_event_object_type > @@ -362,6 +364,8 @@ PyObject *gdbpy_frame_stop_reason_string (PyObject *, PyObject *); >  PyObject *gdbpy_lookup_symbol (PyObject *self, PyObject *args, PyObject *kw); >  PyObject *gdbpy_lookup_global_symbol (PyObject *self, PyObject *args, >                        PyObject *kw); > +PyObject *gdbpy_lookup_minimal_symbol (PyObject *self, PyObject *args, > +                       PyObject *kw); >  PyObject *gdbpy_newest_frame (PyObject *self, PyObject *args); >  PyObject *gdbpy_selected_frame (PyObject *self, PyObject *args); >  PyObject *gdbpy_block_for_pc (PyObject *self, PyObject *args); > @@ -436,6 +440,8 @@ int gdbpy_initialize_commands (void) >    CPYCHECKER_NEGATIVE_RESULT_SETS_EXCEPTION; >  int gdbpy_initialize_symbols (void) >   
CPYCHECKER_NEGATIVE_RESULT_SETS_EXCEPTION; > +int gdbpy_initialize_minsymbols (void) > +  CPYCHECKER_NEGATIVE_RESULT_SETS_EXCEPTION; >  int gdbpy_initialize_symtabs (void) >    CPYCHECKER_NEGATIVE_RESULT_SETS_EXCEPTION; >  int gdbpy_initialize_blocks (void) > diff --git a/gdb/python/python.c b/gdb/python/python.c > index 6cbe5f0..30a86e1 100644 > --- a/gdb/python/python.c > +++ b/gdb/python/python.c > @@ -1800,6 +1800,7 @@ message == an error message without a stack will be printed."), >        || gdbpy_initialize_frames () < 0 >        || gdbpy_initialize_commands () < 0 >        || gdbpy_initialize_symbols () < 0 > +      || gdbpy_initialize_minsymbols () < 0 >        || gdbpy_initialize_symtabs () < 0 >        || gdbpy_initialize_blocks () < 0 >        || gdbpy_initialize_functions () < 0 > @@ -2025,6 +2026,10 @@ a boolean indicating if name is a field of the current implied argument\n\ >      METH_VARARGS | METH_KEYWORDS, >      "lookup_global_symbol (name [, domain]) ->
symbol\n\ >  Return the symbol corresponding to the given name (or None)." }, > +{ "lookup_minimal_symbol", (PyCFunction) gdbpy_lookup_minimal_symbol, > +    METH_VARARGS | METH_KEYWORDS, > +    "lookup_minimal_symbol (name) -> minsym\n\ > +Return the symbol corresponding to the given name (or None)." }, >  >    { "lookup_objfile", (PyCFunction) gdbpy_lookup_objfile, >      METH_VARARGS | METH_KEYWORDS,


This needs a set of tests and documentation.

Cheers

Phil


^ permalink raw reply	[flat|nested] 17+ messages in thread

* Re: [PATCH 2/7] py-value: properly handle unsigned and pointer types
  2016-02-05 12:12   ` Phil Muldoon
@ 2016-02-05 12:29     ` Phil Muldoon
  0 siblings, 0 replies; 17+ messages in thread
From: Phil Muldoon @ 2016-02-05 12:29 UTC (permalink / raw)
  To: jeffm, gdb-patches

> > Thanks. This needs tests and documentation changes for the changes in functionality. > > Cheers > > Phil

Something really weird is happening after my recent Fedora 23 install
with patch wrapping. I'll resend the replies when I've fixed it!

Cheers

Phil

^ permalink raw reply	[flat|nested] 17+ messages in thread

* Re: [PATCH 4/7] py-symbol: Require a frame for lookup_symbol only when necessary
  2016-02-05 12:17   ` Phil Muldoon
@ 2016-02-05 16:08     ` Jeff Mahoney
  0 siblings, 0 replies; 17+ messages in thread
From: Jeff Mahoney @ 2016-02-05 16:08 UTC (permalink / raw)
  To: Phil Muldoon, gdb-patches

-----BEGIN PGP SIGNED MESSAGE-----
Hash: SHA1

On 2/5/16 7:17 AM, Phil Muldoon wrote:
> On 04/02/16 17:29, jeffm@suse.com wrote:
>> From: Jeff Mahoney <jeffm@suse.com> > > gdbpy_lookup_symbol
>> requires a frame prior to doing the symbol lookup but > a frame
>> isn't necessary for many symbol types.  Calling >
>> symbol_read_needs_frame will tell us if it's necessary but we
>> need to > have already looked up the symbol to use it.  This
>> patch puts the > lookup first and then only resolves the frame if
>> one is required. > > This allows us to lookup static symbols
>> directly from python rather > than using gdb.eval_and_parse.
> 
> Please add documentation and further tests for new functionality.
> 
>> --- >  gdb/python/py-symbol.c | 31
>> +++++++++++++++++-------------- >  1 file changed, 17
>> insertions(+), 14 deletions(-) > > diff --git
>> a/gdb/python/py-symbol.c b/gdb/python/py-symbol.c > index
>> cbbc9e2..c7f0ff8 100644 > --- a/gdb/python/py-symbol.c > +++
>> b/gdb/python/py-symbol.c > @@ -382,14 +382,28 @@
>> gdbpy_lookup_symbol (PyObject *self, PyObject *args, PyObject
>> *kw) >  >    if (block_obj) >      block = block_object_to_block
>> (block_obj); > -  else > + > +  TRY > +    { > +      symbol =
>> lookup_symbol (name, block, (domain_enum) domain, > +
>> &is_a_field_of_this).symbol; > +    } > +  CATCH (except,
>> RETURN_MASK_ALL) > +    { > +      GDB_PY_HANDLE_EXCEPTION
>> (except); > +    } > +  END_CATCH > + > +  if (symbol && !block)
>> >      { >        struct frame_info *selected_frame; >  >
>> TRY >      { > -      selected_frame = get_selected_frame (_("No
>> frame selected.")); > -      block = get_frame_block
>> (selected_frame, NULL); > +      if
> (symbol_read_needs_frame(symbol)) {
> 
> Formatting nit, space after function name and before (.
> 
>> +        selected_frame = get_selected_frame (_("No frame
>> selected.")); > +        block = get_frame_block (selected_frame,
>> NULL); > +      } >      } >        CATCH (except,
>> RETURN_MASK_ALL) >      { > @@ -398,17 +412,6 @@
>> gdbpy_lookup_symbol (PyObject *self, PyObject *args, PyObject
>> *kw) >        END_CATCH >      }
> 
> My only concern here is (and the context is not meaningful enough
> to see), is that you've removed an "else" above which is an
> unconditional branch, and replaced it with an IF instead. What
> happens when both IFs can fail?

This patch is broken.  It works for my need to look up static symbols
but it fails the py-symbol testsuite.  We look up the block and never
use it, so it's no wonder it's failing.

- -Jeff


- -- 
Jeff Mahoney
SUSE Labs
-----BEGIN PGP SIGNATURE-----
Version: GnuPG/MacGPG2 v2.0.19 (Darwin)
Comment: GPGTools - http://gpgtools.org

iQIcBAEBAgAGBQJWtMjbAAoJEB57S2MheeWyJhcQALzkE3DaXUyTHxaSovnUbe6+
bFleikXDjbL4UKYwT/0iJfVoaH8weoWMiFfrYVXJgCqXIUEX9mtUPfMXq5NHyJ71
0FgQa9pRVCK2sS/4jpPjMwL40AU4DI4XYOHbSowZfm9kn28yY+uP6UkbiWsv5dDn
egNkSzjyrX4MzMHSzZIDqNBGqPdp03nLBKyrjl8iLtgUK6HZwBponk2Y50l8d+gy
M6FP4xXMUqKgW0JBW+P1V/S6YowW+RCaHgBrmwISe9QU79M3s3Jpi+VD+WxEO8HY
rUrlOXzJhMm/IcF9r4ROmYGXFdQdOjlMyTQtOkyCe8+VYlwOsc107GzipNnQ2mRf
Rd2+2UZNs+430pcpivq+h+wDlcM5Cu6QWDFa9/TIHw97n776YeQ6bZHcSCXFOvd2
FrWsOqQoM2zNTKTjuxCJyr2lfgHxFTiSggVrX1Glmw2sVdwks5DvoGXNa8lnq1fp
PGII0edxMPg1neOhZZ24j/k2dB1dZmAOMuzUg6OggSiVSj31R+ZmarE/xRHfXqPk
kTfuJHX45dpBTZQ+X6VgWkYzG6OHhRV2ilWHky7PETM3LTpTVFNGqOxEEYZach0/
C5SV6Zykp+wjkZTVLL/q3YgPRHJj+SUKRRBEj7qfG4PcyeI0ybsDVfQ8ZEh6JANI
WWRyy3/zyUbONSV77I/R
=eJFa
-----END PGP SIGNATURE-----

^ permalink raw reply	[flat|nested] 17+ messages in thread

* Re: [PATCH 4/7] py-symbol: Require a frame for lookup_symbol only when necessary
  2016-02-04 17:29 ` [PATCH 4/7] py-symbol: Require a frame for lookup_symbol only when necessary jeffm
  2016-02-05 12:17   ` Phil Muldoon
@ 2016-02-05 16:35   ` Phil Muldoon
  1 sibling, 0 replies; 17+ messages in thread
From: Phil Muldoon @ 2016-02-05 16:35 UTC (permalink / raw)
  To: jeffm, gdb-patches

On 04/02/16 17:29, jeffm@suse.com wrote:
> From: Jeff Mahoney <jeffm@suse.com>
>
> gdbpy_lookup_symbol requires a frame prior to doing the symbol lookup but
> a frame isn't necessary for many symbol types.  Calling
> symbol_read_needs_frame will tell us if it's necessary but we need to
> have already looked up the symbol to use it.  This patch puts the
> lookup first and then only resolves the frame if one is required.
>
> This allows us to lookup static symbols directly from python rather
> than using gdb.eval_and_parse.

Thanks. I've rewritten this patch email reply from the garbled so hopefully you
can make sense of it! ;)

All of these patches need documentation in the user manual, and also new tests
for functionality.

> ---
>  gdb/python/py-symbol.c | 31 +++++++++++++++++--------------
>  1 file changed, 17 insertions(+), 14 deletions(-)
>
> diff --git a/gdb/python/py-symbol.c b/gdb/python/py-symbol.c
> index cbbc9e2..c7f0ff8 100644
> --- a/gdb/python/py-symbol.c
> +++ b/gdb/python/py-symbol.c
> @@ -382,14 +382,28 @@ gdbpy_lookup_symbol (PyObject *self, PyObject *args, PyObject *kw)
>  
>    if (block_obj)
>      block = block_object_to_block (block_obj);
> -  else
> +
> +  TRY
> +    {
> +      symbol = lookup_symbol (name, block, (domain_enum) domain,
> +			      &is_a_field_of_this).symbol;
> +    }
> +  CATCH (except, RETURN_MASK_ALL)
> +    {
> +      GDB_PY_HANDLE_EXCEPTION (except);
> +    }
> +  END_CATCH
> +
> +  if (symbol && !block)
>      {
>        struct frame_info *selected_frame;
>  
>        TRY
>  	{
> -	  selected_frame = get_selected_frame (_("No frame selected."));
> -	  block = get_frame_block (selected_frame, NULL);
> +	  if (symbol_read_needs_frame(symbol)) {

Space after the function name and before the (. This and others.
> +	    selected_frame = get_selected_frame (_("No frame selected."));
> +	    block = get_frame_block (selected_frame, NULL);
> +	  }
>  	}
>        CATCH (except, RETURN_MASK_ALL)
>  	{
> @@ -398,17 +412,6 @@ gdbpy_lookup_symbol (PyObject *self, PyObject *args, PyObject *kw)
>        END_CATCH
>      }
>  
> -  TRY
> -    {
> -      symbol = lookup_symbol (name, block, (domain_enum) domain,
> -			      &is_a_field_of_this).symbol;
> -    }
> -  CATCH (except, RETURN_MASK_ALL)
> -    {
> -      GDB_PY_HANDLE_EXCEPTION (except);
> -    }
> -  END_CATCH
> -
>    ret_tuple = PyTuple_New (2);
>    if (!ret_tuple)
>      return NULL;

My only concern here is (and the context is not meaningful enough to
see), is that you've removed an "else" above which is an unconditional
branch, and replaced it with an IF instead. What happens when both IFs
can fail?

Cheers

Phil

^ permalink raw reply	[flat|nested] 17+ messages in thread

* Re: [PATCH 6/7] py-minsymbol: Add interface to access minimal_symbols
  2016-02-04 17:29 ` [PATCH 6/7] py-minsymbol: Add interface to access minimal_symbols jeffm
  2016-02-05 12:25   ` Phil Muldoon
@ 2016-02-05 16:43   ` Phil Muldoon
  2016-02-08 15:51     ` Jeff Mahoney
  1 sibling, 1 reply; 17+ messages in thread
From: Phil Muldoon @ 2016-02-05 16:43 UTC (permalink / raw)
  To: jeffm, gdb-patches

On 04/02/16 17:29, jeffm@suse.com wrote:
> From: Jeff Mahoney <jeffm@suse.com>
>
> This patch adds a new gdb.MinSymbol object to export the minimal_symbol
> interface.  These objects can be resolved using a new
> gdb.lookup_minimal_symbol call.
> ---
>  gdb/Makefile.in              |   6 +
>  gdb/python/py-minsymbol.c    | 390 +++++++++++++++++++++++++++++++++++++++++++
>  gdb/python/python-internal.h |   6 +
>  gdb/python/python.c          |   5 +
>  4 files changed, 407 insertions(+)
>  create mode 100644 gdb/python/py-minsymbol.c
>
> diff --git a/gdb/Makefile.in b/gdb/Makefile.in
> index 3eadbbc..c2f7eef 100644
> --- a/gdb/Makefile.in
> +++ b/gdb/Makefile.in
> @@ -400,6 +400,7 @@ SUBDIR_PYTHON_OBS = \
>  	py-infthread.o \
>  	py-lazy-string.o \
>  	py-linetable.o \
> +	py-minsymbol.o \
>  	py-newobjfileevent.o \
>  	py-objfile.o \
>  	py-param.o \
> @@ -440,6 +441,7 @@ SUBDIR_PYTHON_SRCS = \
>  	python/py-infthread.c \
>  	python/py-lazy-string.c \
>  	python/py-linetable.c \
> +	python/py-minsymbol.c \
>  	python/py-newobjfileevent.c \
>  	python/py-objfile.c \
>  	python/py-param.c \
> @@ -2635,6 +2637,10 @@ py-linetable.o: $(srcdir)/python/py-linetable.c
>  	$(COMPILE) $(PYTHON_CFLAGS) $(srcdir)/python/py-linetable.c
>  	$(POSTCOMPILE)
>  
> +py-minsymbol.o: $(srcdir)/python/py-minsymbol.c
> +	$(COMPILE) $(PYTHON_CFLAGS) $(srcdir)/python/py-minsymbol.c
> +	$(POSTCOMPILE)
> +
>  py-newobjfileevent.o: $(srcdir)/python/py-newobjfileevent.c
>  	$(COMPILE) $(PYTHON_CFLAGS) $(srcdir)/python/py-newobjfileevent.c
>  	$(POSTCOMPILE)
> diff --git a/gdb/python/py-minsymbol.c b/gdb/python/py-minsymbol.c
> new file mode 100644
> index 0000000..d8b56bc
> --- /dev/null
> +++ b/gdb/python/py-minsymbol.c
> @@ -0,0 +1,390 @@
> +/* Python interface to minsymbols.
> +
> +   Copyright (C) 2008-2013 Free Software Foundation, Inc.
Wrong Copyright date.

> +
> +   This file is part of GDB.
> +
> +   This program is free software; you can redistribute it and/or modify
> +   it under the terms of the GNU General Public License as published by
> +   the Free Software Foundation; either version 3 of the License, or
> +   (at your option) any later version.
> +
> +   This program is distributed in the hope that it will be useful,
> +   but WITHOUT ANY WARRANTY; without even the implied warranty of
> +   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
> +   GNU General Public License for more details.
> +
> +   You should have received a copy of the GNU General Public License
> +   along with this program.  If not, see <http://www.gnu.org/licenses/>.  */
> +
> +#include "defs.h"
> +#include "block.h"
> +#include "exceptions.h"
> +#include "frame.h"
> +#include "symtab.h"
> +#include "python-internal.h"
> +#include "objfiles.h"
> +#include "value.h"
> +
> +typedef struct msympy_symbol_object {
> +  PyObject_HEAD
> +  /* The GDB minimal_symbol structure this object is wrapping.  */
> +  struct minimal_symbol *minsym;
> +  struct objfile *objfile;
> +
> +  struct type *type;
> +  /* A symbol object is associated with an objfile, so keep track with
> +     doubly-linked list, rooted in the objfile.  This lets us
> +     invalidate the underlying struct minimal_symbol when the objfile is
> +     deleted.  */
> +  struct msympy_symbol_object *prev;
> +  struct msympy_symbol_object *next;
> +} minsym_object;
Can you please document all members of a struct here.
> +/* Return the symbol that is wrapped by this symbol object.  */
> +static struct minimal_symbol *
> +minsym_object_to_minsym (PyObject *obj)
> +{
> +  if (! PyObject_TypeCheck (obj, &minsym_object_type))
> +    return NULL;
> +  return ((minsym_object *) obj)->minsym;
> +}
> +
> +static struct objfile *
> +minsym_object_to_objfile (PyObject *obj)
> +{
> +  if (! PyObject_TypeCheck (obj, &minsym_object_type))
> +    return NULL;
> +  return ((minsym_object *) obj)->objfile;
> +}
> +
> +/* Require a valid symbol.  All access to minsym_object->symbol should be
> +   gated by this call.  */
> +#define MSYMPY_REQUIRE_VALID(minsym_obj, minsym)	\
> +  do {							\
> +    minsym = minsym_object_to_minsym (minsym_obj);	\
> +    if (minsym == NULL)				\
> +      {							\
> +	PyErr_SetString (PyExc_RuntimeError,		\
> +			 _("MinSymbol is invalid."));	\
> +	return NULL;					\
> +      }							\
> +  } while (0)
> +
> +#define MSYMPY_REQUIRE_VALID_BOUND(minsym_obj, minsym, objfile)	\
> +  do {								\
> +    minsym = minsym_object_to_minsym (minsym_obj);		\
> +    objfile = minsym_object_to_objfile (minsym_obj);		\
> +    if (minsym == NULL || objfile == NULL)			\
> +      {								\
> +	PyErr_SetString (PyExc_RuntimeError,			\
> +			 _("MinSymbol is invalid."));		\
> +	return NULL;						\
> +      }								\
> +  } while (0)
> +
> +static PyObject *
> +msympy_str (PyObject *self)
> +{
> +  PyObject *result;
> +  struct minimal_symbol *minsym = NULL;
> +
> +  MSYMPY_REQUIRE_VALID (self, minsym);
> +
> +  result = PyString_FromString (MSYMBOL_PRINT_NAME (minsym));
> +
> +  return result;
> +}
> +
> +static PyObject *
> +msympy_get_name (PyObject *self, void *closure)
> +{
> +  struct minimal_symbol *minsym = NULL;
> +
> +  MSYMPY_REQUIRE_VALID (self, minsym);
> +
> +  return PyString_FromString (MSYMBOL_NATURAL_NAME (minsym));
> +}
> +
> +static PyObject *
> +msympy_get_file_name (PyObject *self, void *closure)
> +{
> +  struct minimal_symbol *minsym = NULL;
> +
> +  MSYMPY_REQUIRE_VALID (self, minsym);
> +
> +  return PyString_FromString (minsym->filename);
> +}
> +
> +static PyObject *
> +msympy_get_linkage_name (PyObject *self, void *closure)
> +{
> +  struct minimal_symbol *minsym = NULL;
> +
> +  MSYMPY_REQUIRE_VALID (self, minsym);
> +
> +  return PyString_FromString (MSYMBOL_LINKAGE_NAME (minsym));
> +}
> +
> +static PyObject *
> +msympy_get_print_name (PyObject *self, void *closure)
> +{
> +  struct minimal_symbol *minsym = NULL;
> +
> +  MSYMPY_REQUIRE_VALID (self, minsym);
> +
> +  return msympy_str (self);
> +}
> +
> +static PyObject *
> +msympy_get_section (PyObject *self, void *closure)
> +{
> +  struct minimal_symbol *minsym = NULL;
> +  struct objfile *objfile = NULL;
> +  struct obj_section *section;
> +  const char *name;
> +
> +  MSYMPY_REQUIRE_VALID_BOUND (self, minsym, objfile);
> +
> +  section = MSYMBOL_OBJ_SECTION (objfile, minsym);
> +  if (section) 
The { on a newline.
> {
> +    name = bfd_section_name (objfile->obfd, section->the_bfd_section);
> +    if (name)
> +      return PyString_FromString (name);
> +  }
> +
> +  Py_RETURN_NONE;
> +
> +}
> +
> +static PyObject *
> +msympy_is_valid (PyObject *self, PyObject *args)
> +{
> +  struct minimal_symbol *minsym = NULL;
> +
> +  minsym = minsym_object_to_minsym (self);
> +  if (minsym == NULL)
> +    Py_RETURN_FALSE;
> +
> +  Py_RETURN_TRUE;
> +}
> +
> +/* Implementation of gdb.MinSymbol.value (self) -> gdb.Value.  Returns
> +   the value of the symbol, or an error in various circumstances.  */
> +
> +static PyObject *
> +msympy_value (PyObject *self, PyObject *args)
> +{
> +  minsym_object *minsym_obj = (minsym_object *)self;
> +  struct minimal_symbol *minsym = NULL;
> +  struct value *value = NULL;
> +
> +  if (!PyArg_ParseTuple (args, ""))
> +    return NULL;
> +
> +  MSYMPY_REQUIRE_VALID (self, minsym);
> +  TRY
> +    {
> +      value = value_from_ulongest(minsym_obj->type,
> +				  MSYMBOL_VALUE_RAW_ADDRESS(minsym));
Space after function name and before (. This and other places.

The patch series, in principle, looks fine to me other than the nits I've highlighted.

However it needs tests for the new functionality.  It would be helpful if you could indicate if you have run the testsuite
and checked for regressions.

It also needs documentation additions and changes, and a documentation review.

Also please wait for a maintainer to sign off on it, too

Cheers

Phil

^ permalink raw reply	[flat|nested] 17+ messages in thread

* Re: [PATCH 6/7] py-minsymbol: Add interface to access minimal_symbols
  2016-02-05 16:43   ` Phil Muldoon
@ 2016-02-08 15:51     ` Jeff Mahoney
  0 siblings, 0 replies; 17+ messages in thread
From: Jeff Mahoney @ 2016-02-08 15:51 UTC (permalink / raw)
  To: Phil Muldoon, gdb-patches

-----BEGIN PGP SIGNED MESSAGE-----
Hash: SHA1

On 2/5/16 11:43 AM, Phil Muldoon wrote:
> On 04/02/16 17:29, jeffm@suse.com wrote:
>> From: Jeff Mahoney <jeffm@suse.com>
>> 
>> This patch adds a new gdb.MinSymbol object to export the
>> minimal_symbol interface.  These objects can be resolved using a
>> new gdb.lookup_minimal_symbol call. --- +static PyObject * 
>> +msympy_get_file_name (PyObject *self, void *closure) +{ +
>> struct minimal_symbol *minsym = NULL; + +  MSYMPY_REQUIRE_VALID
>> (self, minsym); + +  return PyString_FromString
>> (minsym->filename); +}

In writing the test cases, I discovered that this value usually (but
not always) has a value but the value tends to be meaningless or at
least compiler dependent.  In my test program, it dumps asm("...")
code into crtstuff.c.  I tried using an assembly file instead (with
generic pseudoinstructions and labels) and it presented an empty
filename.  When I load up the kernel, it puts every minimal symbol in
csum-wrappers_64.c (at least for this kernel build).  Given the
questionable utility of this value, should I even keep it?

[Removed other details for review; I have addressed them in each patch.]

> The patch series, in principle, looks fine to me other than the
> nits I've highlighted.
> 
> However it needs tests for the new functionality.  It would be
> helpful if you could indicate if you have run the testsuite and
> checked for regressions.
> 
> It also needs documentation additions and changes, and a
> documentation review.
> 
> Also please wait for a maintainer to sign off on it, too

Thanks for the review.  I've added tests and documentation for all but
regcache (which I'm about to do) and it already sussed out several
bugs.  I ended up having to rework the gdb.lookup_symbol for static
symbols patch significantly since it did introduce regressions.  It's
a lot simpler now.  I'll post the updated set once I finish up regcache.

- -Jeff

- -- 
Jeff Mahoney
SUSE Labs
-----BEGIN PGP SIGNATURE-----
Version: GnuPG/MacGPG2 v2.0.19 (Darwin)
Comment: GPGTools - http://gpgtools.org

iQIcBAEBAgAGBQJWuLl7AAoJEB57S2MheeWySVsQAICvXs3bfkMCTXa6pnWHra+z
s+tKiyC6gjOX2U2bDzZq3uxSdbArtB3Rgl4TTRs3BFAAOdVLwsMw0jCEZjaNZQO1
D0qwErfrD0E7RF+YKKslako8+Au+yAMcqlQt97XnQFURSLHQ3Dp/jGyRRH9qSXo4
kFatHeKUlhX8gV2nkc7xwKTddxGnUSSHCb02UWcZOZ7Mjaa4ORVpvmWTHp5KdLWJ
S4AGzR4G/JB90ew31aZriAFqQbQTHMcauOhoMSktLobAMsVRX/zX6/CLXNntOPoT
tI8YK834H+DMGJVYzqOx9uqaxtTo8E84IMVMG4X1XIkgd1au4qQeuEyyfGdwfE0Z
Iun5rgCVaGtg8VxCB66jfDloImlfYbwZgGnN/+oWHlhTHurko5ma7xgV/mDgoUUw
J0v/m0yZ8pmMYtVSK2eWBcrKQcqdoKRa+XGqwa69/vWTwD0LnxUA8tphA61XOn3m
x26tHsokAXGmXy+RBrCMYa+ABehBcB5AQFZYxTHCPFF5qJlJs5MYT29+HdxsS71N
A/iHoJWaPPiM8FqmqLGexnS1rxClwd4DK7hiwq43b5gbfw4axXPp3l6AC1nQ++4M
ZPHz18KmlVRkgiNcAxMXwMCxGW04cbWkD/VrhnMk8TnNWYDWZyabIAXJnKTeJKIU
0Qox9ZHBecYHXtL0ADCu
=1A6j
-----END PGP SIGNATURE-----

^ permalink raw reply	[flat|nested] 17+ messages in thread

end of thread, other threads:[~2016-02-08 15:51 UTC | newest]

Thread overview: 17+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2016-02-04 17:29 [PATCH 0/7] Python extension patchset jeffm
2016-02-04 17:29 ` [PATCH 6/7] py-minsymbol: Add interface to access minimal_symbols jeffm
2016-02-05 12:25   ` Phil Muldoon
2016-02-05 16:43   ` Phil Muldoon
2016-02-08 15:51     ` Jeff Mahoney
2016-02-04 17:29 ` [PATCH 4/7] py-symbol: Require a frame for lookup_symbol only when necessary jeffm
2016-02-05 12:17   ` Phil Muldoon
2016-02-05 16:08     ` Jeff Mahoney
2016-02-05 16:35   ` Phil Muldoon
2016-02-04 17:29 ` [PATCH 1/7] check_types_equal: short circuit check if identical pointers are used jeffm
2016-02-04 17:29 ` [PATCH 3/7] py-symbol: use Py_RETURN_NONE instead of open coding it jeffm
2016-02-04 17:29 ` [PATCH 7/7] py-regcache: Add interface to regcache jeffm
2016-02-04 17:43 ` [PATCH 2/7] py-value: properly handle unsigned and pointer types jeffm
2016-02-05 12:12   ` Phil Muldoon
2016-02-05 12:29     ` Phil Muldoon
2016-02-04 17:43 ` [PATCH 5/7] py-symbol: export section name jeffm
2016-02-05 12:18   ` Phil Muldoon

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for read-only IMAP folder(s) and NNTP newsgroup(s).