]> Git Repo - binutils.git/blob - gdb/python/py-varobj.c
gdb: remove SYMBOL_CLASS macro, add getter
[binutils.git] / gdb / python / py-varobj.c
1 /* Copyright (C) 2013-2022 Free Software Foundation, Inc.
2
3    This program is free software; you can redistribute it and/or modify
4    it under the terms of the GNU General Public License as published by
5    the Free Software Foundation; either version 3 of the License, or
6    (at your option) any later version.
7
8    This program is distributed in the hope that it will be useful,
9    but WITHOUT ANY WARRANTY; without even the implied warranty of
10    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
11    GNU General Public License for more details.
12
13    You should have received a copy of the GNU General Public License
14    along with this program.  If not, see <http://www.gnu.org/licenses/>.  */
15
16 #include "defs.h"
17 #include "python-internal.h"
18 #include "varobj.h"
19 #include "varobj-iter.h"
20
21 /* A dynamic varobj iterator "class" for python pretty-printed
22    varobjs.  This inherits struct varobj_iter.  */
23
24 struct py_varobj_iter : public varobj_iter
25 {
26   py_varobj_iter (struct varobj *var, gdbpy_ref<> &&pyiter);
27   ~py_varobj_iter () override;
28
29   std::unique_ptr<varobj_item> next () override;
30
31 private:
32
33   /* The varobj this iterator is listing children for.  */
34   struct varobj *m_var;
35
36   /* The next raw index we will try to check is available.  If it is
37      equal to number_of_children, then we've already iterated the
38      whole set.  */
39   int m_next_raw_index = 0;
40
41   /* The python iterator returned by the printer's 'children' method,
42      or NULL if not available.  */
43   PyObject *m_iter;
44 };
45
46 /* Implementation of the 'dtor' method of pretty-printed varobj
47    iterators.  */
48
49 py_varobj_iter::~py_varobj_iter ()
50 {
51   gdbpy_enter_varobj enter_py (m_var);
52   Py_XDECREF (m_iter);
53 }
54
55 /* Implementation of the 'next' method of pretty-printed varobj
56    iterators.  */
57
58 std::unique_ptr<varobj_item>
59 py_varobj_iter::next ()
60 {
61   PyObject *py_v;
62   varobj_item *vitem;
63   const char *name = NULL;
64
65   if (!gdb_python_initialized)
66     return NULL;
67
68   gdbpy_enter_varobj enter_py (m_var);
69
70   gdbpy_ref<> item (PyIter_Next (m_iter));
71
72   if (item == NULL)
73     {
74       /* Normal end of iteration.  */
75       if (!PyErr_Occurred ())
76         return NULL;
77
78       /* If we got a memory error, just use the text as the item.  */
79       if (PyErr_ExceptionMatches (gdbpy_gdb_memory_error))
80         {
81           gdbpy_err_fetch fetched_error;
82           gdb::unique_xmalloc_ptr<char> value_str = fetched_error.to_string ();
83           if (value_str == NULL)
84             {
85               gdbpy_print_stack ();
86               return NULL;
87             }
88
89           std::string name_str = string_printf ("<error at %d>",
90                                                 m_next_raw_index++);
91           item.reset (Py_BuildValue ("(ss)", name_str.c_str (),
92                                      value_str.get ()));
93           if (item == NULL)
94             {
95               gdbpy_print_stack ();
96               return NULL;
97             }
98         }
99       else
100         {
101           /* Any other kind of error.  */
102           gdbpy_print_stack ();
103           return NULL;
104         }
105     }
106
107   if (!PyArg_ParseTuple (item.get (), "sO", &name, &py_v))
108     {
109       gdbpy_print_stack ();
110       error (_("Invalid item from the child list"));
111     }
112
113   vitem = new varobj_item ();
114   vitem->value = release_value (convert_value_from_python (py_v));
115   if (vitem->value == NULL)
116     gdbpy_print_stack ();
117   vitem->name = name;
118
119   m_next_raw_index++;
120   return std::unique_ptr<varobj_item> (vitem);
121 }
122
123 /* Constructor of pretty-printed varobj iterators.  VAR is the varobj
124    whose children the iterator will be iterating over.  PYITER is the
125    python iterator actually responsible for the iteration.  */
126
127 py_varobj_iter::py_varobj_iter (struct varobj *var, gdbpy_ref<> &&pyiter)
128   : m_var (var),
129     m_iter (pyiter.release ())
130 {
131 }
132
133 /* Return a new pretty-printed varobj iterator suitable to iterate
134    over VAR's children.  */
135
136 std::unique_ptr<varobj_iter>
137 py_varobj_get_iterator (struct varobj *var, PyObject *printer)
138 {
139   gdbpy_enter_varobj enter_py (var);
140
141   if (!PyObject_HasAttr (printer, gdbpy_children_cst))
142     return NULL;
143
144   gdbpy_ref<> children (PyObject_CallMethodObjArgs (printer, gdbpy_children_cst,
145                                                     NULL));
146   if (children == NULL)
147     {
148       gdbpy_print_stack ();
149       error (_("Null value returned for children"));
150     }
151
152   gdbpy_ref<> iter (PyObject_GetIter (children.get ()));
153   if (iter == NULL)
154     {
155       gdbpy_print_stack ();
156       error (_("Could not get children iterator"));
157     }
158
159   return std::unique_ptr<varobj_iter> (new py_varobj_iter (var,
160                                                            std::move (iter)));
161 }
This page took 0.033564 seconds and 4 git commands to generate.