GDB (xrefs)
py-lazy-string.c
Go to the documentation of this file.
1 /* Python interface to lazy strings.
2 
3  Copyright (C) 2010-2018 Free Software Foundation, Inc.
4 
5  This file is part of GDB.
6 
7  This program is free software; you can redistribute it and/or modify
8  it under the terms of the GNU General Public License as published by
9  the Free Software Foundation; either version 3 of the License, or
10  (at your option) any later version.
11 
12  This program is distributed in the hope that it will be useful,
13  but WITHOUT ANY WARRANTY; without even the implied warranty of
14  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15  GNU General Public License for more details.
16 
17  You should have received a copy of the GNU General Public License
18  along with this program. If not, see <http://www.gnu.org/licenses/>. */
19 
20 #include "defs.h"
21 #include "python-internal.h"
22 #include "charset.h"
23 #include "value.h"
24 #include "valprint.h"
25 #include "language.h"
26 
27 typedef struct {
28  PyObject_HEAD
29 
30  /* Holds the address of the lazy string. */
32 
33  /* Holds the encoding that will be applied to the string
34  when the string is printed by GDB. If the encoding is set
35  to None then GDB will select the most appropriate
36  encoding when the sting is printed. */
37  char *encoding;
38 
39  /* If TYPE is an array: If the length is known, then this value is the
40  array's length, otherwise it is -1.
41  If TYPE is not an array: Then this value represents the string's length.
42  In either case, if the value is -1 then the string will be fetched and
43  encoded up to the first null of appropriate width. */
44  long length;
45 
46  /* This attribute holds the type of the string.
47  For example if the lazy string was created from a C "char*" then TYPE
48  represents a C "char*".
49  To get the type of the character in the string call
50  stpy_lazy_string_elt_type.
51  This is recorded as a PyObject so that we take advantage of support for
52  preserving the type should its owning objfile go away. */
53  PyObject *type;
55 
56 extern PyTypeObject lazy_string_object_type
57  CPYCHECKER_TYPE_OBJECT_FOR_TYPEDEF ("lazy_string_object");
58 
59 static PyObject *
60 stpy_get_address (PyObject *self, void *closure)
61 {
62  lazy_string_object *self_string = (lazy_string_object *) self;
63 
64  return gdb_py_long_from_ulongest (self_string->address);
65 }
66 
67 static PyObject *
68 stpy_get_encoding (PyObject *self, void *closure)
69 {
70  lazy_string_object *self_string = (lazy_string_object *) self;
71  PyObject *result;
72 
73  /* An encoding can be set to NULL by the user, so check before
74  attempting a Python FromString call. If NULL return Py_None. */
75  if (self_string->encoding)
76  result = PyString_FromString (self_string->encoding);
77  else
78  {
79  result = Py_None;
80  Py_INCREF (result);
81  }
82 
83  return result;
84 }
85 
86 static PyObject *
87 stpy_get_length (PyObject *self, void *closure)
88 {
89  lazy_string_object *self_string = (lazy_string_object *) self;
90 
91  return PyLong_FromLong (self_string->length);
92 }
93 
94 static PyObject *
95 stpy_get_type (PyObject *self, void *closure)
96 {
97  lazy_string_object *str_obj = (lazy_string_object *) self;
98 
99  Py_INCREF (str_obj->type);
100  return str_obj->type;
101 }
102 
103 static PyObject *
104 stpy_convert_to_value (PyObject *self, PyObject *args)
105 {
106  lazy_string_object *self_string = (lazy_string_object *) self;
107  struct value *val = NULL;
108 
109  if (self_string->address == 0)
110  {
111  PyErr_SetString (gdbpy_gdb_memory_error,
112  _("Cannot create a value from NULL."));
113  return NULL;
114  }
115 
116  TRY
117  {
118  struct type *type = type_object_to_type (self_string->type);
119  struct type *realtype;
120 
121  gdb_assert (type != NULL);
122  realtype = check_typedef (type);
123  switch (TYPE_CODE (realtype))
124  {
125  case TYPE_CODE_PTR:
126  /* If a length is specified we need to convert this to an array
127  of the specified size. */
128  if (self_string->length != -1)
129  {
130  /* PR 20786: There's no way to specify an array of length zero.
131  Record a length of [0,-1] which is how Ada does it. Anything
132  we do is broken, but this is one possible solution. */
134  0, self_string->length - 1);
135  val = value_at_lazy (type, self_string->address);
136  }
137  else
138  val = value_from_pointer (type, self_string->address);
139  break;
140  default:
141  val = value_at_lazy (type, self_string->address);
142  break;
143  }
144  }
145  CATCH (except, RETURN_MASK_ALL)
146  {
147  GDB_PY_HANDLE_EXCEPTION (except);
148  }
149  END_CATCH
150 
151  return value_to_value_object (val);
152 }
153 
154 static void
155 stpy_dealloc (PyObject *self)
156 {
157  lazy_string_object *self_string = (lazy_string_object *) self;
158 
159  xfree (self_string->encoding);
160 }
161 
162 /* Low level routine to create a <gdb.LazyString> object.
163 
164  Note: If TYPE is an array, LENGTH either must be -1 (meaning to use the
165  size of the array, which may itself be unknown in which case a length of
166  -1 is still used) or must be the length of the array. */
167 
168 PyObject *
170  const char *encoding, struct type *type)
171 {
172  lazy_string_object *str_obj = NULL;
173  struct type *realtype;
174 
175  if (length < -1)
176  {
177  PyErr_SetString (PyExc_ValueError, _("Invalid length."));
178  return NULL;
179  }
180 
181  if (address == 0 && length != 0)
182  {
183  PyErr_SetString (gdbpy_gdb_memory_error,
184  _("Cannot create a lazy string with address 0x0, " \
185  "and a non-zero length."));
186  return NULL;
187  }
188 
189  if (!type)
190  {
191  PyErr_SetString (PyExc_RuntimeError,
192  _("A lazy string's type cannot be NULL."));
193  return NULL;
194  }
195 
196  realtype = check_typedef (type);
197  switch (TYPE_CODE (realtype))
198  {
199  case TYPE_CODE_ARRAY:
200  {
201  LONGEST array_length = -1;
202  LONGEST low_bound, high_bound;
203 
204  if (get_array_bounds (realtype, &low_bound, &high_bound))
205  array_length = high_bound - low_bound + 1;
206  if (length == -1)
207  length = array_length;
208  else if (length != array_length)
209  {
210  PyErr_SetString (PyExc_ValueError, _("Invalid length."));
211  return NULL;
212  }
213  break;
214  }
215  }
216 
217  str_obj = PyObject_New (lazy_string_object, &lazy_string_object_type);
218  if (!str_obj)
219  return NULL;
220 
221  str_obj->address = address;
222  str_obj->length = length;
223  if (encoding == NULL || !strcmp (encoding, ""))
224  str_obj->encoding = NULL;
225  else
226  str_obj->encoding = xstrdup (encoding);
227  str_obj->type = type_to_type_object (type);
228 
229  return (PyObject *) str_obj;
230 }
231 
232 int
234 {
235  if (PyType_Ready (&lazy_string_object_type) < 0)
236  return -1;
237 
238  Py_INCREF (&lazy_string_object_type);
239  return 0;
240 }
241 
242 /* Determine whether the printer object pointed to by OBJ is a
243  Python lazy string. */
244 int
245 gdbpy_is_lazy_string (PyObject *result)
246 {
247  return PyObject_TypeCheck (result, &lazy_string_object_type);
248 }
249 
250 /* Return the type of a character in lazy string LAZY. */
251 
252 static struct type *
254 {
255  struct type *type = type_object_to_type (lazy->type);
256  struct type *realtype;
257 
258  gdb_assert (type != NULL);
259  realtype = check_typedef (type);
260 
261  switch (TYPE_CODE (realtype))
262  {
263  case TYPE_CODE_PTR:
264  case TYPE_CODE_ARRAY:
265  return TYPE_TARGET_TYPE (realtype);
266  default:
267  /* This is done to preserve existing behaviour. PR 20769.
268  E.g., gdb.parse_and_eval("my_int_variable").lazy_string().type. */
269  return realtype;
270  }
271 }
272 
273 /* Extract the parameters from the lazy string object STRING.
274  ENCODING may be set to NULL, if no encoding is found. */
275 
276 void
277 gdbpy_extract_lazy_string (PyObject *string, CORE_ADDR *addr,
278  struct type **str_elt_type,
279  long *length,
281 {
282  lazy_string_object *lazy;
283 
284  gdb_assert (gdbpy_is_lazy_string (string));
285 
286  lazy = (lazy_string_object *) string;
287 
288  *addr = lazy->address;
289  *str_elt_type = stpy_lazy_string_elt_type (lazy);
290  *length = lazy->length;
291  encoding->reset (lazy->encoding ? xstrdup (lazy->encoding) : NULL);
292 }
293 
294 
295 
296 static PyMethodDef lazy_string_object_methods[] = {
297  { "value", stpy_convert_to_value, METH_NOARGS,
298  "Create a (lazy) value that contains a pointer to the string." },
299  {NULL} /* Sentinel */
300 };
301 
302 
304  { "address", stpy_get_address, NULL, "Address of the string.", NULL },
305  { "encoding", stpy_get_encoding, NULL, "Encoding of the string.", NULL },
306  { "length", stpy_get_length, NULL, "Length of the string.", NULL },
307  { "type", stpy_get_type, NULL, "Type associated with the string.", NULL },
308  { NULL } /* Sentinel */
309 };
310 
311 PyTypeObject lazy_string_object_type = {
312  PyVarObject_HEAD_INIT (NULL, 0)
313  "gdb.LazyString", /*tp_name*/
314  sizeof (lazy_string_object), /*tp_basicsize*/
315  0, /*tp_itemsize*/
316  stpy_dealloc, /*tp_dealloc*/
317  0, /*tp_print*/
318  0, /*tp_getattr*/
319  0, /*tp_setattr*/
320  0, /*tp_compare*/
321  0, /*tp_repr*/
322  0, /*tp_as_number*/
323  0, /*tp_as_sequence*/
324  0, /*tp_as_mapping*/
325  0, /*tp_hash */
326  0, /*tp_call*/
327  0, /*tp_str*/
328  0, /*tp_getattro*/
329  0, /*tp_setattro*/
330  0, /*tp_as_buffer*/
331  Py_TPFLAGS_DEFAULT, /*tp_flags*/
332  "GDB lazy string object", /* tp_doc */
333  0, /* tp_traverse */
334  0, /* tp_clear */
335  0, /* tp_richcompare */
336  0, /* tp_weaklistoffset */
337  0, /* tp_iter */
338  0, /* tp_iternext */
339  lazy_string_object_methods, /* tp_methods */
340  0, /* tp_members */
341  lazy_string_object_getset /* tp_getset */
342 };
unsigned int length
Definition: gdbtypes.h:803
static PyObject * stpy_get_encoding(PyObject *self, void *closure)
struct type * lookup_array_range_type(struct type *element_type, LONGEST low_bound, LONGEST high_bound)
Definition: gdbtypes.c:1232
static PyObject * stpy_get_address(PyObject *self, void *closure)
static PyObject * stpy_convert_to_value(PyObject *self, PyObject *args)
bfd_vma CORE_ADDR
Definition: common-types.h:41
void xfree(void *)
struct type * type_object_to_type(PyObject *obj)
Definition: py-type.c:1332
int gdbpy_initialize_lazy_string(void)
#define gdb_py_long_from_ulongest
static struct type * stpy_lazy_string_elt_type(lazy_string_object *lazy)
#define _(String)
Definition: gdb_locale.h:35
#define PyVarObject_HEAD_INIT(type, size)
PyTypeObject lazy_string_object_type CPYCHECKER_TYPE_OBJECT_FOR_TYPEDEF("lazy_string_object")
#define END_CATCH
static void stpy_dealloc(PyObject *self)
#define GDB_PY_HANDLE_EXCEPTION(Exception)
static PyMethodDef lazy_string_object_methods[]
#define TRY
struct type * check_typedef(struct type *type)
Definition: gdbtypes.c:2421
#define CATCH(EXCEPTION, MASK)
std::unique_ptr< T, xfree_deleter< T > > unique_xmalloc_ptr
static gdb_PyGetSetDef lazy_string_object_getset[]
Definition: gdbtypes.h:749
PyObject * value_to_value_object(struct value *val)
Definition: py-value.c:1579
struct value * value_at_lazy(struct type *type, CORE_ADDR addr)
Definition: valops.c:944
#define gdb_assert(expr)
Definition: gdb_assert.h:32
Definition: value.c:169
static PyObject * stpy_get_length(PyObject *self, void *closure)
struct value * value_from_pointer(struct type *type, CORE_ADDR addr)
Definition: value.c:3560
void gdbpy_extract_lazy_string(PyObject *string, CORE_ADDR *addr, struct type **str_elt_type, long *length, gdb::unique_xmalloc_ptr< char > *encoding)
#define TYPE_TARGET_TYPE(thistype)
Definition: gdbtypes.h:1226
#define TYPE_CODE(thistype)
Definition: gdbtypes.h:1238
PyTypeObject lazy_string_object_type
int gdbpy_is_lazy_string(PyObject *result)
PyObject * gdbpy_gdb_memory_error
Definition: python.c:134
PyObject * gdbpy_create_lazy_string_object(CORE_ADDR address, long length, const char *encoding, struct type *type)
static PyObject * stpy_get_type(PyObject *self, void *closure)
PyObject_HEAD CORE_ADDR address
int get_array_bounds(struct type *type, LONGEST *low_bound, LONGEST *high_bound)
Definition: gdbtypes.c:1056
long long LONGEST
Definition: common-types.h:52
PyObject * type_to_type_object(struct type *type)
Definition: py-type.c:1320