]> Git Repo - binutils.git/blob - gdb/python/py-symtab.c
Automatic date update in version.in
[binutils.git] / gdb / python / py-symtab.c
1 /* Python interface to symbol tables.
2
3    Copyright (C) 2008-2022 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 "charset.h"
22 #include "symtab.h"
23 #include "source.h"
24 #include "python-internal.h"
25 #include "objfiles.h"
26 #include "block.h"
27
28 struct symtab_object {
29   PyObject_HEAD
30   /* The GDB Symbol table structure.  */
31   struct symtab *symtab;
32   /* A symtab object is associated with an objfile, so keep track with
33      a doubly-linked list, rooted in the objfile.  This allows
34      invalidation of the underlying struct symtab when the objfile is
35      deleted.  */
36   symtab_object *prev;
37   symtab_object *next;
38 };
39
40 /* This function is called when an objfile is about to be freed.
41    Invalidate the symbol table as further actions on the symbol table
42    would result in bad data.  All access to obj->symtab should be
43    gated by STPY_REQUIRE_VALID which will raise an exception on
44    invalid symbol tables.  */
45 struct stpy_deleter
46 {
47   void operator() (symtab_object *obj)
48   {
49     while (obj)
50       {
51         symtab_object *next = obj->next;
52
53         obj->symtab = NULL;
54         obj->next = NULL;
55         obj->prev = NULL;
56         obj = next;
57       }
58   }
59 };
60
61 extern PyTypeObject symtab_object_type
62     CPYCHECKER_TYPE_OBJECT_FOR_TYPEDEF ("symtab_object");
63 static const registry<objfile>::key<symtab_object, stpy_deleter>
64      stpy_objfile_data_key;
65
66 /* Require a valid symbol table.  All access to symtab_object->symtab
67    should be gated by this call.  */
68 #define STPY_REQUIRE_VALID(symtab_obj, symtab)           \
69   do {                                                   \
70     symtab = symtab_object_to_symtab (symtab_obj);       \
71     if (symtab == NULL)                                  \
72       {                                                  \
73         PyErr_SetString (PyExc_RuntimeError,             \
74                          _("Symbol Table is invalid.")); \
75         return NULL;                                     \
76       }                                                  \
77   } while (0)
78
79 struct sal_object {
80   PyObject_HEAD
81   /* The GDB Symbol table structure.  */
82   PyObject *symtab;
83   /* The GDB Symbol table and line structure.  */
84   struct symtab_and_line *sal;
85   /* A Symtab and line object is associated with an objfile, so keep
86      track with a doubly-linked list, rooted in the objfile.  This
87      allows invalidation of the underlying struct symtab_and_line
88      when the objfile is deleted.  */
89   sal_object *prev;
90   sal_object *next;
91 };
92
93 /* This is called when an objfile is about to be freed.  Invalidate
94    the sal object as further actions on the sal would result in bad
95    data.  All access to obj->sal should be gated by
96    SALPY_REQUIRE_VALID which will raise an exception on invalid symbol
97    table and line objects.  */
98 struct salpy_deleter
99 {
100   void operator() (sal_object *obj)
101   {
102     gdbpy_enter enter_py;
103
104     while (obj)
105       {
106         sal_object *next = obj->next;
107
108         gdbpy_ref<> tmp (obj->symtab);
109         obj->symtab = Py_None;
110         Py_INCREF (Py_None);
111
112         obj->next = NULL;
113         obj->prev = NULL;
114         xfree (obj->sal);
115         obj->sal = NULL;
116
117         obj = next;
118       }
119   }
120 };
121
122 extern PyTypeObject sal_object_type
123     CPYCHECKER_TYPE_OBJECT_FOR_TYPEDEF ("sal_object");
124 static const registry<objfile>::key<sal_object, salpy_deleter>
125      salpy_objfile_data_key;
126
127 /* Require a valid symbol table and line object.  All access to
128    sal_object->sal should be gated by this call.  */
129 #define SALPY_REQUIRE_VALID(sal_obj, sal)                               \
130   do {                                                                  \
131     sal = sal_object_to_symtab_and_line (sal_obj);                      \
132     if (sal == NULL)                                                    \
133       {                                                                 \
134           PyErr_SetString (PyExc_RuntimeError,                          \
135                            _("Symbol Table and Line is invalid."));     \
136           return NULL;                                                  \
137         }                                                               \
138   } while (0)
139
140 static PyObject *
141 stpy_str (PyObject *self)
142 {
143   PyObject *result;
144   struct symtab *symtab = NULL;
145
146   STPY_REQUIRE_VALID (self, symtab);
147
148   result = PyUnicode_FromString (symtab_to_filename_for_display (symtab));
149
150   return result;
151 }
152
153 static PyObject *
154 stpy_get_filename (PyObject *self, void *closure)
155 {
156   PyObject *str_obj;
157   struct symtab *symtab = NULL;
158   const char *filename;
159
160   STPY_REQUIRE_VALID (self, symtab);
161   filename = symtab_to_filename_for_display (symtab);
162
163   str_obj = host_string_to_python_string (filename).release ();
164   return str_obj;
165 }
166
167 static PyObject *
168 stpy_get_objfile (PyObject *self, void *closure)
169 {
170   struct symtab *symtab = NULL;
171
172   STPY_REQUIRE_VALID (self, symtab);
173
174   return objfile_to_objfile_object (symtab->compunit ()->objfile ()).release ();
175 }
176
177 /* Getter function for symtab.producer.  */
178
179 static PyObject *
180 stpy_get_producer (PyObject *self, void *closure)
181 {
182   struct symtab *symtab = NULL;
183   struct compunit_symtab *cust;
184
185   STPY_REQUIRE_VALID (self, symtab);
186   cust = symtab->compunit ();
187   if (cust->producer () != nullptr)
188     {
189       const char *producer = cust->producer ();
190
191       return host_string_to_python_string (producer).release ();
192     }
193
194   Py_RETURN_NONE;
195 }
196
197 static PyObject *
198 stpy_fullname (PyObject *self, PyObject *args)
199 {
200   const char *fullname;
201   struct symtab *symtab = NULL;
202
203   STPY_REQUIRE_VALID (self, symtab);
204
205   fullname = symtab_to_fullname (symtab);
206
207   return host_string_to_python_string (fullname).release ();
208 }
209
210 /* Implementation of gdb.Symtab.is_valid (self) -> Boolean.
211    Returns True if this Symbol table still exists in GDB.  */
212
213 static PyObject *
214 stpy_is_valid (PyObject *self, PyObject *args)
215 {
216   struct symtab *symtab = NULL;
217
218   symtab = symtab_object_to_symtab (self);
219   if (symtab == NULL)
220     Py_RETURN_FALSE;
221
222   Py_RETURN_TRUE;
223 }
224
225 /* Return the GLOBAL_BLOCK of the underlying symtab.  */
226
227 static PyObject *
228 stpy_global_block (PyObject *self, PyObject *args)
229 {
230   struct symtab *symtab = NULL;
231   const struct blockvector *blockvector;
232
233   STPY_REQUIRE_VALID (self, symtab);
234
235   blockvector = symtab->compunit ()->blockvector ();
236   const struct block *block = blockvector->global_block ();
237
238   return block_to_block_object (block, symtab->compunit ()->objfile ());
239 }
240
241 /* Return the STATIC_BLOCK of the underlying symtab.  */
242
243 static PyObject *
244 stpy_static_block (PyObject *self, PyObject *args)
245 {
246   struct symtab *symtab = NULL;
247   const struct blockvector *blockvector;
248
249   STPY_REQUIRE_VALID (self, symtab);
250
251   blockvector = symtab->compunit ()->blockvector ();
252   const struct block *block = blockvector->static_block ();
253
254   return block_to_block_object (block, symtab->compunit ()->objfile ());
255 }
256
257 /* Implementation of gdb.Symtab.linetable (self) -> gdb.LineTable.
258    Returns a gdb.LineTable object corresponding to this symbol
259    table.  */
260
261 static PyObject *
262 stpy_get_linetable (PyObject *self, PyObject *args)
263 {
264   struct symtab *symtab = NULL;
265
266   STPY_REQUIRE_VALID (self, symtab);
267
268   return symtab_to_linetable_object (self);
269 }
270
271 static PyObject *
272 salpy_str (PyObject *self)
273 {
274   const char *filename;
275   sal_object *sal_obj;
276   struct symtab_and_line *sal = NULL;
277
278   SALPY_REQUIRE_VALID (self, sal);
279
280   sal_obj = (sal_object *) self;
281   if (sal_obj->symtab == Py_None)
282     filename = "<unknown>";
283   else
284     {
285       symtab *symtab = symtab_object_to_symtab (sal_obj->symtab);
286       filename = symtab_to_filename_for_display (symtab);
287     }
288
289   return PyUnicode_FromFormat ("symbol and line for %s, line %d", filename,
290                                sal->line);
291 }
292
293 static void
294 stpy_dealloc (PyObject *obj)
295 {
296   symtab_object *symtab = (symtab_object *) obj;
297
298   if (symtab->prev)
299     symtab->prev->next = symtab->next;
300   else if (symtab->symtab)
301     stpy_objfile_data_key.set (symtab->symtab->compunit ()->objfile (),
302                                symtab->next);
303   if (symtab->next)
304     symtab->next->prev = symtab->prev;
305   symtab->symtab = NULL;
306   Py_TYPE (obj)->tp_free (obj);
307 }
308
309
310 static PyObject *
311 salpy_get_pc (PyObject *self, void *closure)
312 {
313   struct symtab_and_line *sal = NULL;
314
315   SALPY_REQUIRE_VALID (self, sal);
316
317   return gdb_py_object_from_ulongest (sal->pc).release ();
318 }
319
320 /* Implementation of the get method for the 'last' attribute of
321    gdb.Symtab_and_line.  */
322
323 static PyObject *
324 salpy_get_last (PyObject *self, void *closure)
325 {
326   struct symtab_and_line *sal = NULL;
327
328   SALPY_REQUIRE_VALID (self, sal);
329
330   if (sal->end > 0)
331     return gdb_py_object_from_ulongest (sal->end - 1).release ();
332   else
333     Py_RETURN_NONE;
334 }
335
336 static PyObject *
337 salpy_get_line (PyObject *self, void *closure)
338 {
339   struct symtab_and_line *sal = NULL;
340
341   SALPY_REQUIRE_VALID (self, sal);
342
343   return gdb_py_object_from_longest (sal->line).release ();
344 }
345
346 static PyObject *
347 salpy_get_symtab (PyObject *self, void *closure)
348 {
349   struct symtab_and_line *sal;
350   sal_object *self_sal = (sal_object *) self;
351
352   SALPY_REQUIRE_VALID (self, sal);
353
354   Py_INCREF (self_sal->symtab);
355
356   return (PyObject *) self_sal->symtab;
357 }
358
359 /* Implementation of gdb.Symtab_and_line.is_valid (self) -> Boolean.
360    Returns True if this Symbol table and line object still exists GDB.  */
361
362 static PyObject *
363 salpy_is_valid (PyObject *self, PyObject *args)
364 {
365   struct symtab_and_line *sal;
366
367   sal = sal_object_to_symtab_and_line (self);
368   if (sal == NULL)
369     Py_RETURN_FALSE;
370
371   Py_RETURN_TRUE;
372 }
373
374 static void
375 salpy_dealloc (PyObject *self)
376 {
377   sal_object *self_sal = (sal_object *) self;
378
379   if (self_sal->prev)
380     self_sal->prev->next = self_sal->next;
381   else if (self_sal->symtab != Py_None)
382     salpy_objfile_data_key.set
383       (symtab_object_to_symtab (self_sal->symtab)->compunit ()->objfile (),
384        self_sal->next);
385
386   if (self_sal->next)
387     self_sal->next->prev = self_sal->prev;
388
389   Py_DECREF (self_sal->symtab);
390   xfree (self_sal->sal);
391   Py_TYPE (self)->tp_free (self);
392 }
393
394 /* Given a sal, and a sal_object that has previously been allocated
395    and initialized, populate the sal_object with the struct sal data.
396    Also, register the sal_object life-cycle with the life-cycle of the
397    object file associated with this sal, if needed.  If a failure
398    occurs during the sal population, this function will return -1.  */
399 static int CPYCHECKER_NEGATIVE_RESULT_SETS_EXCEPTION
400 set_sal (sal_object *sal_obj, struct symtab_and_line sal)
401 {
402   PyObject *symtab_obj;
403
404   if (sal.symtab)
405     {
406       symtab_obj = symtab_to_symtab_object  (sal.symtab);
407       /* If a symtab existed in the sal, but it cannot be duplicated,
408          we exit.  */
409       if (symtab_obj == NULL)
410         return -1;
411     }
412   else
413     {
414       symtab_obj = Py_None;
415       Py_INCREF (Py_None);
416     }
417
418   sal_obj->sal = ((struct symtab_and_line *)
419                   xmemdup (&sal, sizeof (struct symtab_and_line),
420                            sizeof (struct symtab_and_line)));
421   sal_obj->symtab = symtab_obj;
422   sal_obj->prev = NULL;
423
424   /* If the SAL does not have a symtab, we do not add it to the
425      objfile cleanup observer linked list.  */
426   if (sal_obj->symtab != Py_None)
427     {
428       symtab *symtab = symtab_object_to_symtab (sal_obj->symtab);
429
430       sal_obj->next
431         = salpy_objfile_data_key.get (symtab->compunit ()->objfile ());
432       if (sal_obj->next)
433         sal_obj->next->prev = sal_obj;
434
435       salpy_objfile_data_key.set (symtab->compunit ()->objfile (), sal_obj);
436     }
437   else
438     sal_obj->next = NULL;
439
440   return 0;
441 }
442
443 /* Given a symtab, and a symtab_object that has previously been
444    allocated and initialized, populate the symtab_object with the
445    struct symtab data.  Also, register the symtab_object life-cycle
446    with the life-cycle of the object file associated with this
447    symtab, if needed.  */
448 static void
449 set_symtab (symtab_object *obj, struct symtab *symtab)
450 {
451   obj->symtab = symtab;
452   obj->prev = NULL;
453   if (symtab)
454     {
455       obj->next = stpy_objfile_data_key.get (symtab->compunit ()->objfile ());
456       if (obj->next)
457         obj->next->prev = obj;
458       stpy_objfile_data_key.set (symtab->compunit ()->objfile (), obj);
459     }
460   else
461     obj->next = NULL;
462 }
463
464 /* Create a new symbol table (gdb.Symtab) object that encapsulates the
465    symtab structure from GDB.  */
466 PyObject *
467 symtab_to_symtab_object (struct symtab *symtab)
468 {
469   symtab_object *symtab_obj;
470
471   symtab_obj = PyObject_New (symtab_object, &symtab_object_type);
472   if (symtab_obj)
473     set_symtab (symtab_obj, symtab);
474
475   return (PyObject *) symtab_obj;
476 }
477
478 /* Create a new symtab and line (gdb.Symtab_and_line) object
479    that encapsulates the symtab_and_line structure from GDB.  */
480 PyObject *
481 symtab_and_line_to_sal_object (struct symtab_and_line sal)
482 {
483   gdbpy_ref<sal_object> sal_obj (PyObject_New (sal_object, &sal_object_type));
484   if (sal_obj != NULL)
485     {
486       if (set_sal (sal_obj.get (), sal) < 0)
487         return NULL;
488     }
489
490   return (PyObject *) sal_obj.release ();
491 }
492
493 /* Return struct symtab_and_line reference that is wrapped by this
494    object.  */
495 struct symtab_and_line *
496 sal_object_to_symtab_and_line (PyObject *obj)
497 {
498   if (! PyObject_TypeCheck (obj, &sal_object_type))
499     return NULL;
500   return ((sal_object *) obj)->sal;
501 }
502
503 /* Return struct symtab reference that is wrapped by this object.  */
504 struct symtab *
505 symtab_object_to_symtab (PyObject *obj)
506 {
507   if (! PyObject_TypeCheck (obj, &symtab_object_type))
508     return NULL;
509   return ((symtab_object *) obj)->symtab;
510 }
511
512 int
513 gdbpy_initialize_symtabs (void)
514 {
515   symtab_object_type.tp_new = PyType_GenericNew;
516   if (PyType_Ready (&symtab_object_type) < 0)
517     return -1;
518
519   sal_object_type.tp_new = PyType_GenericNew;
520   if (PyType_Ready (&sal_object_type) < 0)
521     return -1;
522
523   if (gdb_pymodule_addobject (gdb_module, "Symtab",
524                               (PyObject *) &symtab_object_type) < 0)
525     return -1;
526
527   return gdb_pymodule_addobject (gdb_module, "Symtab_and_line",
528                                  (PyObject *) &sal_object_type);
529 }
530
531 \f
532
533 static gdb_PyGetSetDef symtab_object_getset[] = {
534   { "filename", stpy_get_filename, NULL,
535     "The symbol table's source filename.", NULL },
536   { "objfile", stpy_get_objfile, NULL, "The symtab's objfile.",
537     NULL },
538   { "producer", stpy_get_producer, NULL,
539     "The name/version of the program that compiled this symtab.", NULL },
540   {NULL}  /* Sentinel */
541 };
542
543 static PyMethodDef symtab_object_methods[] = {
544   { "is_valid", stpy_is_valid, METH_NOARGS,
545     "is_valid () -> Boolean.\n\
546 Return true if this symbol table is valid, false if not." },
547   { "fullname", stpy_fullname, METH_NOARGS,
548     "fullname () -> String.\n\
549 Return the symtab's full source filename." },
550   { "global_block", stpy_global_block, METH_NOARGS,
551     "global_block () -> gdb.Block.\n\
552 Return the global block of the symbol table." },
553   { "static_block", stpy_static_block, METH_NOARGS,
554     "static_block () -> gdb.Block.\n\
555 Return the static block of the symbol table." },
556     { "linetable", stpy_get_linetable, METH_NOARGS,
557     "linetable () -> gdb.LineTable.\n\
558 Return the LineTable associated with this symbol table" },
559   {NULL}  /* Sentinel */
560 };
561
562 PyTypeObject symtab_object_type = {
563   PyVarObject_HEAD_INIT (NULL, 0)
564   "gdb.Symtab",                   /*tp_name*/
565   sizeof (symtab_object),         /*tp_basicsize*/
566   0,                              /*tp_itemsize*/
567   stpy_dealloc,                   /*tp_dealloc*/
568   0,                              /*tp_print*/
569   0,                              /*tp_getattr*/
570   0,                              /*tp_setattr*/
571   0,                              /*tp_compare*/
572   0,                              /*tp_repr*/
573   0,                              /*tp_as_number*/
574   0,                              /*tp_as_sequence*/
575   0,                              /*tp_as_mapping*/
576   0,                              /*tp_hash */
577   0,                              /*tp_call*/
578   stpy_str,                       /*tp_str*/
579   0,                              /*tp_getattro*/
580   0,                              /*tp_setattro*/
581   0,                              /*tp_as_buffer*/
582   Py_TPFLAGS_DEFAULT,             /*tp_flags*/
583   "GDB symtab object",            /*tp_doc */
584   0,                              /*tp_traverse */
585   0,                              /*tp_clear */
586   0,                              /*tp_richcompare */
587   0,                              /*tp_weaklistoffset */
588   0,                              /*tp_iter */
589   0,                              /*tp_iternext */
590   symtab_object_methods,          /*tp_methods */
591   0,                              /*tp_members */
592   symtab_object_getset            /*tp_getset */
593 };
594
595 static gdb_PyGetSetDef sal_object_getset[] = {
596   { "symtab", salpy_get_symtab, NULL, "Symtab object.", NULL },
597   { "pc", salpy_get_pc, NULL, "Return the symtab_and_line's pc.", NULL },
598   { "last", salpy_get_last, NULL,
599     "Return the symtab_and_line's last address.", NULL },
600   { "line", salpy_get_line, NULL,
601     "Return the symtab_and_line's line.", NULL },
602   {NULL}  /* Sentinel */
603 };
604
605 static PyMethodDef sal_object_methods[] = {
606   { "is_valid", salpy_is_valid, METH_NOARGS,
607     "is_valid () -> Boolean.\n\
608 Return true if this symbol table and line is valid, false if not." },
609   {NULL}  /* Sentinel */
610 };
611
612 PyTypeObject sal_object_type = {
613   PyVarObject_HEAD_INIT (NULL, 0)
614   "gdb.Symtab_and_line",          /*tp_name*/
615   sizeof (sal_object),            /*tp_basicsize*/
616   0,                              /*tp_itemsize*/
617   salpy_dealloc,                  /*tp_dealloc*/
618   0,                              /*tp_print*/
619   0,                              /*tp_getattr*/
620   0,                              /*tp_setattr*/
621   0,                              /*tp_compare*/
622   0,                              /*tp_repr*/
623   0,                              /*tp_as_number*/
624   0,                              /*tp_as_sequence*/
625   0,                              /*tp_as_mapping*/
626   0,                              /*tp_hash */
627   0,                              /*tp_call*/
628   salpy_str,                      /*tp_str*/
629   0,                              /*tp_getattro*/
630   0,                              /*tp_setattro*/
631   0,                              /*tp_as_buffer*/
632   Py_TPFLAGS_DEFAULT,             /*tp_flags*/
633   "GDB symtab_and_line object",   /*tp_doc */
634   0,                              /*tp_traverse */
635   0,                              /*tp_clear */
636   0,                              /*tp_richcompare */
637   0,                              /*tp_weaklistoffset */
638   0,                              /*tp_iter */
639   0,                              /*tp_iternext */
640   sal_object_methods,             /*tp_methods */
641   0,                              /*tp_members */
642   sal_object_getset               /*tp_getset */
643 };
This page took 0.059868 seconds and 4 git commands to generate.