GDB (API)
/home/stan/gdb/src/gdb/python/py-symbol.c
Go to the documentation of this file.
00001 /* Python interface to symbols.
00002 
00003    Copyright (C) 2008-2013 Free Software Foundation, Inc.
00004 
00005    This file is part of GDB.
00006 
00007    This program is free software; you can redistribute it and/or modify
00008    it under the terms of the GNU General Public License as published by
00009    the Free Software Foundation; either version 3 of the License, or
00010    (at your option) any later version.
00011 
00012    This program is distributed in the hope that it will be useful,
00013    but WITHOUT ANY WARRANTY; without even the implied warranty of
00014    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
00015    GNU General Public License for more details.
00016 
00017    You should have received a copy of the GNU General Public License
00018    along with this program.  If not, see <http://www.gnu.org/licenses/>.  */
00019 
00020 #include "defs.h"
00021 #include "block.h"
00022 #include "exceptions.h"
00023 #include "frame.h"
00024 #include "symtab.h"
00025 #include "python-internal.h"
00026 #include "objfiles.h"
00027 
00028 typedef struct sympy_symbol_object {
00029   PyObject_HEAD
00030   /* The GDB symbol structure this object is wrapping.  */
00031   struct symbol *symbol;
00032   /* A symbol object is associated with an objfile, so keep track with
00033      doubly-linked list, rooted in the objfile.  This lets us
00034      invalidate the underlying struct symbol when the objfile is
00035      deleted.  */
00036   struct sympy_symbol_object *prev;
00037   struct sympy_symbol_object *next;
00038 } symbol_object;
00039 
00040 /* Require a valid symbol.  All access to symbol_object->symbol should be
00041    gated by this call.  */
00042 #define SYMPY_REQUIRE_VALID(symbol_obj, symbol)         \
00043   do {                                                  \
00044     symbol = symbol_object_to_symbol (symbol_obj);      \
00045     if (symbol == NULL)                                 \
00046       {                                                 \
00047         PyErr_SetString (PyExc_RuntimeError,            \
00048                          _("Symbol is invalid."));      \
00049         return NULL;                                    \
00050       }                                                 \
00051   } while (0)
00052 
00053 static const struct objfile_data *sympy_objfile_data_key;
00054 
00055 static PyObject *
00056 sympy_str (PyObject *self)
00057 {
00058   PyObject *result;
00059   struct symbol *symbol = NULL;
00060 
00061   SYMPY_REQUIRE_VALID (self, symbol);
00062 
00063   result = PyString_FromString (SYMBOL_PRINT_NAME (symbol));
00064 
00065   return result;
00066 }
00067 
00068 static PyObject *
00069 sympy_get_type (PyObject *self, void *closure)
00070 {
00071   struct symbol *symbol = NULL;
00072 
00073   SYMPY_REQUIRE_VALID (self, symbol);
00074 
00075   if (SYMBOL_TYPE (symbol) == NULL)
00076     {
00077       Py_INCREF (Py_None);
00078       return Py_None;
00079     }
00080 
00081   return type_to_type_object (SYMBOL_TYPE (symbol));
00082 }
00083 
00084 static PyObject *
00085 sympy_get_symtab (PyObject *self, void *closure)
00086 {
00087   struct symbol *symbol = NULL;
00088 
00089   SYMPY_REQUIRE_VALID (self, symbol);
00090 
00091   return symtab_to_symtab_object (SYMBOL_SYMTAB (symbol));
00092 }
00093 
00094 static PyObject *
00095 sympy_get_name (PyObject *self, void *closure)
00096 {
00097   struct symbol *symbol = NULL;
00098 
00099   SYMPY_REQUIRE_VALID (self, symbol);
00100 
00101   return PyString_FromString (SYMBOL_NATURAL_NAME (symbol));
00102 }
00103 
00104 static PyObject *
00105 sympy_get_linkage_name (PyObject *self, void *closure)
00106 {
00107   struct symbol *symbol = NULL;
00108 
00109   SYMPY_REQUIRE_VALID (self, symbol);
00110 
00111   return PyString_FromString (SYMBOL_LINKAGE_NAME (symbol));
00112 }
00113 
00114 static PyObject *
00115 sympy_get_print_name (PyObject *self, void *closure)
00116 {
00117   struct symbol *symbol = NULL;
00118 
00119   SYMPY_REQUIRE_VALID (self, symbol);
00120 
00121   return sympy_str (self);
00122 }
00123 
00124 static PyObject *
00125 sympy_get_addr_class (PyObject *self, void *closure)
00126 {
00127   struct symbol *symbol = NULL;
00128 
00129   SYMPY_REQUIRE_VALID (self, symbol);
00130 
00131   return PyInt_FromLong (SYMBOL_CLASS (symbol));
00132 }
00133 
00134 static PyObject *
00135 sympy_is_argument (PyObject *self, void *closure)
00136 {
00137   struct symbol *symbol = NULL;
00138 
00139   SYMPY_REQUIRE_VALID (self, symbol);
00140 
00141   return PyBool_FromLong (SYMBOL_IS_ARGUMENT (symbol));
00142 }
00143 
00144 static PyObject *
00145 sympy_is_constant (PyObject *self, void *closure)
00146 {
00147   struct symbol *symbol = NULL;
00148   enum address_class class;
00149 
00150   SYMPY_REQUIRE_VALID (self, symbol);
00151 
00152   class = SYMBOL_CLASS (symbol);
00153 
00154   return PyBool_FromLong (class == LOC_CONST || class == LOC_CONST_BYTES);
00155 }
00156 
00157 static PyObject *
00158 sympy_is_function (PyObject *self, void *closure)
00159 {
00160   struct symbol *symbol = NULL;
00161   enum address_class class;
00162 
00163   SYMPY_REQUIRE_VALID (self, symbol);
00164 
00165   class = SYMBOL_CLASS (symbol);
00166 
00167   return PyBool_FromLong (class == LOC_BLOCK);
00168 }
00169 
00170 static PyObject *
00171 sympy_is_variable (PyObject *self, void *closure)
00172 {
00173   struct symbol *symbol = NULL;
00174   enum address_class class;
00175 
00176   SYMPY_REQUIRE_VALID (self, symbol);
00177 
00178   class = SYMBOL_CLASS (symbol);
00179 
00180   return PyBool_FromLong (!SYMBOL_IS_ARGUMENT (symbol)
00181                           && (class == LOC_LOCAL || class == LOC_REGISTER
00182                               || class == LOC_STATIC || class == LOC_COMPUTED
00183                               || class == LOC_OPTIMIZED_OUT));
00184 }
00185 
00186 /* Implementation of gdb.Symbol.needs_frame -> Boolean.
00187    Returns true iff the symbol needs a frame for evaluation.  */
00188 
00189 static PyObject *
00190 sympy_needs_frame (PyObject *self, void *closure)
00191 {
00192   struct symbol *symbol = NULL;
00193   volatile struct gdb_exception except;
00194   int result = 0;
00195 
00196   SYMPY_REQUIRE_VALID (self, symbol);
00197 
00198   TRY_CATCH (except, RETURN_MASK_ALL)
00199     {
00200       result = symbol_read_needs_frame (symbol);
00201     }
00202   GDB_PY_HANDLE_EXCEPTION (except);
00203 
00204   if (result)
00205     Py_RETURN_TRUE;
00206   Py_RETURN_FALSE;
00207 }
00208 
00209 /* Implementation of gdb.Symbol.line -> int.
00210    Returns the line number at which the symbol was defined.  */
00211 
00212 static PyObject *
00213 sympy_line (PyObject *self, void *closure)
00214 {
00215   struct symbol *symbol = NULL;
00216 
00217   SYMPY_REQUIRE_VALID (self, symbol);
00218 
00219   return PyInt_FromLong (SYMBOL_LINE (symbol));
00220 }
00221 
00222 /* Implementation of gdb.Symbol.is_valid (self) -> Boolean.
00223    Returns True if this Symbol still exists in GDB.  */
00224 
00225 static PyObject *
00226 sympy_is_valid (PyObject *self, PyObject *args)
00227 {
00228   struct symbol *symbol = NULL;
00229 
00230   symbol = symbol_object_to_symbol (self);
00231   if (symbol == NULL)
00232     Py_RETURN_FALSE;
00233 
00234   Py_RETURN_TRUE;
00235 }
00236 
00237 /* Implementation of gdb.Symbol.value (self[, frame]) -> gdb.Value.  Returns
00238    the value of the symbol, or an error in various circumstances.  */
00239 
00240 static PyObject *
00241 sympy_value (PyObject *self, PyObject *args)
00242 {
00243   struct symbol *symbol = NULL;
00244   struct frame_info *frame_info = NULL;
00245   PyObject *frame_obj = NULL;
00246   struct value *value = NULL;
00247   volatile struct gdb_exception except;
00248 
00249   if (!PyArg_ParseTuple (args, "|O", &frame_obj))
00250     return NULL;
00251 
00252   if (frame_obj != NULL && !PyObject_TypeCheck (frame_obj, &frame_object_type))
00253     {
00254       PyErr_SetString (PyExc_TypeError, "argument is not a frame");
00255       return NULL;
00256     }
00257 
00258   SYMPY_REQUIRE_VALID (self, symbol);
00259   if (SYMBOL_CLASS (symbol) == LOC_TYPEDEF)
00260     {
00261       PyErr_SetString (PyExc_TypeError, "cannot get the value of a typedef");
00262       return NULL;
00263     }
00264 
00265   TRY_CATCH (except, RETURN_MASK_ALL)
00266     {
00267       if (frame_obj != NULL)
00268         {
00269           frame_info = frame_object_to_frame_info (frame_obj);
00270           if (frame_info == NULL)
00271             error (_("invalid frame"));
00272         }
00273       
00274       if (symbol_read_needs_frame (symbol) && frame_info == NULL)
00275         error (_("symbol requires a frame to compute its value"));
00276 
00277       value = read_var_value (symbol, frame_info);
00278     }
00279   GDB_PY_HANDLE_EXCEPTION (except);
00280 
00281   return value_to_value_object (value);
00282 }
00283 
00284 /* Given a symbol, and a symbol_object that has previously been
00285    allocated and initialized, populate the symbol_object with the
00286    struct symbol data.  Also, register the symbol_object life-cycle
00287    with the life-cycle of the object file associated with this
00288    symbol, if needed.  */
00289 static void
00290 set_symbol (symbol_object *obj, struct symbol *symbol)
00291 {
00292   obj->symbol = symbol;
00293   obj->prev = NULL;
00294   if (SYMBOL_SYMTAB (symbol))
00295     {
00296       obj->next = objfile_data (SYMBOL_SYMTAB (symbol)->objfile,
00297                                 sympy_objfile_data_key);
00298 
00299       if (obj->next)
00300         obj->next->prev = obj;
00301       set_objfile_data (SYMBOL_SYMTAB (symbol)->objfile,
00302                         sympy_objfile_data_key, obj);
00303     }
00304   else
00305     obj->next = NULL;
00306 }
00307 
00308 /* Create a new symbol object (gdb.Symbol) that encapsulates the struct
00309    symbol object from GDB.  */
00310 PyObject *
00311 symbol_to_symbol_object (struct symbol *sym)
00312 {
00313   symbol_object *sym_obj;
00314 
00315   sym_obj = PyObject_New (symbol_object, &symbol_object_type);
00316   if (sym_obj)
00317     set_symbol (sym_obj, sym);
00318 
00319   return (PyObject *) sym_obj;
00320 }
00321 
00322 /* Return the symbol that is wrapped by this symbol object.  */
00323 struct symbol *
00324 symbol_object_to_symbol (PyObject *obj)
00325 {
00326   if (! PyObject_TypeCheck (obj, &symbol_object_type))
00327     return NULL;
00328   return ((symbol_object *) obj)->symbol;
00329 }
00330 
00331 static void
00332 sympy_dealloc (PyObject *obj)
00333 {
00334   symbol_object *sym_obj = (symbol_object *) obj;
00335 
00336   if (sym_obj->prev)
00337     sym_obj->prev->next = sym_obj->next;
00338   else if (sym_obj->symbol && SYMBOL_SYMTAB (sym_obj->symbol))
00339     {
00340       set_objfile_data (SYMBOL_SYMTAB (sym_obj->symbol)->objfile,
00341                         sympy_objfile_data_key, sym_obj->next);
00342     }
00343   if (sym_obj->next)
00344     sym_obj->next->prev = sym_obj->prev;
00345   sym_obj->symbol = NULL;
00346 }
00347 
00348 /* Implementation of
00349    gdb.lookup_symbol (name [, block] [, domain]) -> (symbol, is_field_of_this)
00350    A tuple with 2 elements is always returned.  The first is the symbol
00351    object or None, the second is a boolean with the value of
00352    is_a_field_of_this (see comment in lookup_symbol_in_language).  */
00353 
00354 PyObject *
00355 gdbpy_lookup_symbol (PyObject *self, PyObject *args, PyObject *kw)
00356 {
00357   int domain = VAR_DOMAIN;
00358   struct field_of_this_result is_a_field_of_this;
00359   const char *name;
00360   static char *keywords[] = { "name", "block", "domain", NULL };
00361   struct symbol *symbol = NULL;
00362   PyObject *block_obj = NULL, *ret_tuple, *sym_obj, *bool_obj;
00363   const struct block *block = NULL;
00364   volatile struct gdb_exception except;
00365 
00366   if (! PyArg_ParseTupleAndKeywords (args, kw, "s|O!i", keywords, &name,
00367                                      &block_object_type, &block_obj, &domain))
00368     return NULL;
00369 
00370   if (block_obj)
00371     block = block_object_to_block (block_obj);
00372   else
00373     {
00374       struct frame_info *selected_frame;
00375       volatile struct gdb_exception except;
00376 
00377       TRY_CATCH (except, RETURN_MASK_ALL)
00378         {
00379           selected_frame = get_selected_frame (_("No frame selected."));
00380           block = get_frame_block (selected_frame, NULL);
00381         }
00382       GDB_PY_HANDLE_EXCEPTION (except);
00383     }
00384 
00385   TRY_CATCH (except, RETURN_MASK_ALL)
00386     {
00387       symbol = lookup_symbol (name, block, domain, &is_a_field_of_this);
00388     }
00389   GDB_PY_HANDLE_EXCEPTION (except);
00390 
00391   ret_tuple = PyTuple_New (2);
00392   if (!ret_tuple)
00393     return NULL;
00394 
00395   if (symbol)
00396     {
00397       sym_obj = symbol_to_symbol_object (symbol);
00398       if (!sym_obj)
00399         {
00400           Py_DECREF (ret_tuple);
00401           return NULL;
00402         }
00403     }
00404   else
00405     {
00406       sym_obj = Py_None;
00407       Py_INCREF (Py_None);
00408     }
00409   PyTuple_SET_ITEM (ret_tuple, 0, sym_obj);
00410 
00411   bool_obj = (is_a_field_of_this.type != NULL) ? Py_True : Py_False;
00412   Py_INCREF (bool_obj);
00413   PyTuple_SET_ITEM (ret_tuple, 1, bool_obj);
00414 
00415   return ret_tuple;
00416 }
00417 
00418 /* Implementation of
00419    gdb.lookup_global_symbol (name [, domain]) -> symbol or None.  */
00420 
00421 PyObject *
00422 gdbpy_lookup_global_symbol (PyObject *self, PyObject *args, PyObject *kw)
00423 {
00424   int domain = VAR_DOMAIN;
00425   const char *name;
00426   static char *keywords[] = { "name", "domain", NULL };
00427   struct symbol *symbol = NULL;
00428   PyObject *sym_obj;
00429   volatile struct gdb_exception except;
00430 
00431   if (! PyArg_ParseTupleAndKeywords (args, kw, "s|i", keywords, &name,
00432                                      &domain))
00433     return NULL;
00434 
00435   TRY_CATCH (except, RETURN_MASK_ALL)
00436     {
00437       symbol = lookup_symbol_global (name, NULL, domain);
00438     }
00439   GDB_PY_HANDLE_EXCEPTION (except);
00440 
00441   if (symbol)
00442     {
00443       sym_obj = symbol_to_symbol_object (symbol);
00444       if (!sym_obj)
00445         return NULL;
00446     }
00447   else
00448     {
00449       sym_obj = Py_None;
00450       Py_INCREF (Py_None);
00451     }
00452 
00453   return sym_obj;
00454 }
00455 
00456 /* This function is called when an objfile is about to be freed.
00457    Invalidate the symbol as further actions on the symbol would result
00458    in bad data.  All access to obj->symbol should be gated by
00459    SYMPY_REQUIRE_VALID which will raise an exception on invalid
00460    symbols.  */
00461 static void
00462 del_objfile_symbols (struct objfile *objfile, void *datum)
00463 {
00464   symbol_object *obj = datum;
00465   while (obj)
00466     {
00467       symbol_object *next = obj->next;
00468 
00469       obj->symbol = NULL;
00470       obj->next = NULL;
00471       obj->prev = NULL;
00472 
00473       obj = next;
00474     }
00475 }
00476 
00477 int
00478 gdbpy_initialize_symbols (void)
00479 {
00480   if (PyType_Ready (&symbol_object_type) < 0)
00481     return -1;
00482 
00483   /* Register an objfile "free" callback so we can properly
00484      invalidate symbol when an object file that is about to be
00485      deleted.  */
00486   sympy_objfile_data_key
00487     = register_objfile_data_with_cleanup (NULL, del_objfile_symbols);
00488 
00489   if (PyModule_AddIntConstant (gdb_module, "SYMBOL_LOC_UNDEF", LOC_UNDEF) < 0
00490       || PyModule_AddIntConstant (gdb_module, "SYMBOL_LOC_CONST",
00491                                   LOC_CONST) < 0
00492       || PyModule_AddIntConstant (gdb_module, "SYMBOL_LOC_STATIC",
00493                                   LOC_STATIC) < 0
00494       || PyModule_AddIntConstant (gdb_module, "SYMBOL_LOC_REGISTER",
00495                                   LOC_REGISTER) < 0
00496       || PyModule_AddIntConstant (gdb_module, "SYMBOL_LOC_ARG",
00497                                   LOC_ARG) < 0
00498       || PyModule_AddIntConstant (gdb_module, "SYMBOL_LOC_REF_ARG",
00499                                   LOC_REF_ARG) < 0
00500       || PyModule_AddIntConstant (gdb_module, "SYMBOL_LOC_LOCAL",
00501                                   LOC_LOCAL) < 0
00502       || PyModule_AddIntConstant (gdb_module, "SYMBOL_LOC_TYPEDEF",
00503                                   LOC_TYPEDEF) < 0
00504       || PyModule_AddIntConstant (gdb_module, "SYMBOL_LOC_LABEL",
00505                                   LOC_LABEL) < 0
00506       || PyModule_AddIntConstant (gdb_module, "SYMBOL_LOC_BLOCK",
00507                                   LOC_BLOCK) < 0
00508       || PyModule_AddIntConstant (gdb_module, "SYMBOL_LOC_CONST_BYTES",
00509                                   LOC_CONST_BYTES) < 0
00510       || PyModule_AddIntConstant (gdb_module, "SYMBOL_LOC_UNRESOLVED",
00511                                   LOC_UNRESOLVED) < 0
00512       || PyModule_AddIntConstant (gdb_module, "SYMBOL_LOC_OPTIMIZED_OUT",
00513                                   LOC_OPTIMIZED_OUT) < 0
00514       || PyModule_AddIntConstant (gdb_module, "SYMBOL_LOC_COMPUTED",
00515                                   LOC_COMPUTED) < 0
00516       || PyModule_AddIntConstant (gdb_module, "SYMBOL_LOC_REGPARM_ADDR",
00517                                   LOC_REGPARM_ADDR) < 0
00518       || PyModule_AddIntConstant (gdb_module, "SYMBOL_UNDEF_DOMAIN",
00519                                   UNDEF_DOMAIN) < 0
00520       || PyModule_AddIntConstant (gdb_module, "SYMBOL_VAR_DOMAIN",
00521                                   VAR_DOMAIN) < 0
00522       || PyModule_AddIntConstant (gdb_module, "SYMBOL_STRUCT_DOMAIN",
00523                                   STRUCT_DOMAIN) < 0
00524       || PyModule_AddIntConstant (gdb_module, "SYMBOL_LABEL_DOMAIN",
00525                                   LABEL_DOMAIN) < 0
00526       || PyModule_AddIntConstant (gdb_module, "SYMBOL_VARIABLES_DOMAIN",
00527                                   VARIABLES_DOMAIN) < 0
00528       || PyModule_AddIntConstant (gdb_module, "SYMBOL_FUNCTIONS_DOMAIN",
00529                                   FUNCTIONS_DOMAIN) < 0
00530       || PyModule_AddIntConstant (gdb_module, "SYMBOL_TYPES_DOMAIN",
00531                                   TYPES_DOMAIN) < 0)
00532     return -1;
00533 
00534   return gdb_pymodule_addobject (gdb_module, "Symbol",
00535                                  (PyObject *) &symbol_object_type);
00536 }
00537 
00538 
00539 
00540 static PyGetSetDef symbol_object_getset[] = {
00541   { "type", sympy_get_type, NULL,
00542     "Type of the symbol.", NULL },
00543   { "symtab", sympy_get_symtab, NULL,
00544     "Symbol table in which the symbol appears.", NULL },
00545   { "name", sympy_get_name, NULL,
00546     "Name of the symbol, as it appears in the source code.", NULL },
00547   { "linkage_name", sympy_get_linkage_name, NULL,
00548     "Name of the symbol, as used by the linker (i.e., may be mangled).",
00549     NULL },
00550   { "print_name", sympy_get_print_name, NULL,
00551     "Name of the symbol in a form suitable for output.\n\
00552 This is either name or linkage_name, depending on whether the user asked GDB\n\
00553 to display demangled or mangled names.", NULL },
00554   { "addr_class", sympy_get_addr_class, NULL, "Address class of the symbol." },
00555   { "is_argument", sympy_is_argument, NULL,
00556     "True if the symbol is an argument of a function." },
00557   { "is_constant", sympy_is_constant, NULL,
00558     "True if the symbol is a constant." },
00559   { "is_function", sympy_is_function, NULL,
00560     "True if the symbol is a function or method." },
00561   { "is_variable", sympy_is_variable, NULL,
00562     "True if the symbol is a variable." },
00563   { "needs_frame", sympy_needs_frame, NULL,
00564     "True if the symbol requires a frame for evaluation." },
00565   { "line", sympy_line, NULL,
00566     "The source line number at which the symbol was defined." },
00567   { NULL }  /* Sentinel */
00568 };
00569 
00570 static PyMethodDef symbol_object_methods[] = {
00571   { "is_valid", sympy_is_valid, METH_NOARGS,
00572     "is_valid () -> Boolean.\n\
00573 Return true if this symbol is valid, false if not." },
00574   { "value", sympy_value, METH_VARARGS,
00575     "value ([frame]) -> gdb.Value\n\
00576 Return the value of the symbol." },
00577   {NULL}  /* Sentinel */
00578 };
00579 
00580 PyTypeObject symbol_object_type = {
00581   PyVarObject_HEAD_INIT (NULL, 0)
00582   "gdb.Symbol",                   /*tp_name*/
00583   sizeof (symbol_object),         /*tp_basicsize*/
00584   0,                              /*tp_itemsize*/
00585   sympy_dealloc,                  /*tp_dealloc*/
00586   0,                              /*tp_print*/
00587   0,                              /*tp_getattr*/
00588   0,                              /*tp_setattr*/
00589   0,                              /*tp_compare*/
00590   0,                              /*tp_repr*/
00591   0,                              /*tp_as_number*/
00592   0,                              /*tp_as_sequence*/
00593   0,                              /*tp_as_mapping*/
00594   0,                              /*tp_hash */
00595   0,                              /*tp_call*/
00596   sympy_str,                      /*tp_str*/
00597   0,                              /*tp_getattro*/
00598   0,                              /*tp_setattro*/
00599   0,                              /*tp_as_buffer*/
00600   Py_TPFLAGS_DEFAULT,             /*tp_flags*/
00601   "GDB symbol object",            /*tp_doc */
00602   0,                              /*tp_traverse */
00603   0,                              /*tp_clear */
00604   0,                              /*tp_richcompare */
00605   0,                              /*tp_weaklistoffset */
00606   0,                              /*tp_iter */
00607   0,                              /*tp_iternext */
00608   symbol_object_methods,          /*tp_methods */
00609   0,                              /*tp_members */
00610   symbol_object_getset            /*tp_getset */
00611 };
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Defines