Home | History | Annotate | Line # | Download | only in python
py-inferior.c revision 1.6
      1  1.1  christos /* Python interface to inferiors.
      2  1.1  christos 
      3  1.6  christos    Copyright (C) 2009-2016 Free Software Foundation, Inc.
      4  1.1  christos 
      5  1.1  christos    This file is part of GDB.
      6  1.1  christos 
      7  1.1  christos    This program is free software; you can redistribute it and/or modify
      8  1.1  christos    it under the terms of the GNU General Public License as published by
      9  1.1  christos    the Free Software Foundation; either version 3 of the License, or
     10  1.1  christos    (at your option) any later version.
     11  1.1  christos 
     12  1.1  christos    This program is distributed in the hope that it will be useful,
     13  1.1  christos    but WITHOUT ANY WARRANTY; without even the implied warranty of
     14  1.1  christos    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
     15  1.1  christos    GNU General Public License for more details.
     16  1.1  christos 
     17  1.1  christos    You should have received a copy of the GNU General Public License
     18  1.1  christos    along with this program.  If not, see <http://www.gnu.org/licenses/>.  */
     19  1.1  christos 
     20  1.1  christos #include "defs.h"
     21  1.1  christos #include "gdbcore.h"
     22  1.1  christos #include "gdbthread.h"
     23  1.1  christos #include "inferior.h"
     24  1.1  christos #include "objfiles.h"
     25  1.1  christos #include "observer.h"
     26  1.1  christos #include "python-internal.h"
     27  1.1  christos #include "arch-utils.h"
     28  1.1  christos #include "language.h"
     29  1.1  christos #include "gdb_signals.h"
     30  1.1  christos #include "py-event.h"
     31  1.1  christos #include "py-stopevent.h"
     32  1.1  christos 
     33  1.1  christos struct threadlist_entry {
     34  1.1  christos   thread_object *thread_obj;
     35  1.1  christos   struct threadlist_entry *next;
     36  1.1  christos };
     37  1.1  christos 
     38  1.1  christos typedef struct
     39  1.1  christos {
     40  1.1  christos   PyObject_HEAD
     41  1.1  christos 
     42  1.1  christos   /* The inferior we represent.  */
     43  1.1  christos   struct inferior *inferior;
     44  1.1  christos 
     45  1.1  christos   /* thread_object instances under this inferior.  This list owns a
     46  1.1  christos      reference to each object it contains.  */
     47  1.1  christos   struct threadlist_entry *threads;
     48  1.1  christos 
     49  1.1  christos   /* Number of threads in the list.  */
     50  1.1  christos   int nthreads;
     51  1.1  christos } inferior_object;
     52  1.1  christos 
     53  1.5  christos extern PyTypeObject inferior_object_type
     54  1.1  christos     CPYCHECKER_TYPE_OBJECT_FOR_TYPEDEF ("inferior_object");
     55  1.1  christos 
     56  1.1  christos static const struct inferior_data *infpy_inf_data_key;
     57  1.1  christos 
     58  1.1  christos typedef struct {
     59  1.1  christos   PyObject_HEAD
     60  1.1  christos   void *buffer;
     61  1.1  christos 
     62  1.1  christos   /* These are kept just for mbpy_str.  */
     63  1.1  christos   CORE_ADDR addr;
     64  1.1  christos   CORE_ADDR length;
     65  1.1  christos } membuf_object;
     66  1.1  christos 
     67  1.5  christos extern PyTypeObject membuf_object_type
     68  1.1  christos     CPYCHECKER_TYPE_OBJECT_FOR_TYPEDEF ("membuf_object");
     69  1.1  christos 
     70  1.1  christos /* Require that INFERIOR be a valid inferior ID.  */
     71  1.1  christos #define INFPY_REQUIRE_VALID(Inferior)				\
     72  1.1  christos   do {								\
     73  1.1  christos     if (!Inferior->inferior)					\
     74  1.1  christos       {								\
     75  1.1  christos 	PyErr_SetString (PyExc_RuntimeError,			\
     76  1.1  christos 			 _("Inferior no longer exists."));	\
     77  1.1  christos 	return NULL;						\
     78  1.1  christos       }								\
     79  1.1  christos   } while (0)
     80  1.1  christos 
     81  1.1  christos static void
     82  1.1  christos python_on_normal_stop (struct bpstats *bs, int print_frame)
     83  1.1  christos {
     84  1.1  christos   struct cleanup *cleanup;
     85  1.1  christos   enum gdb_signal stop_signal;
     86  1.1  christos 
     87  1.1  christos   if (!gdb_python_initialized)
     88  1.1  christos     return;
     89  1.1  christos 
     90  1.1  christos   if (!find_thread_ptid (inferior_ptid))
     91  1.1  christos       return;
     92  1.1  christos 
     93  1.1  christos   stop_signal = inferior_thread ()->suspend.stop_signal;
     94  1.1  christos 
     95  1.1  christos   cleanup = ensure_python_env (get_current_arch (), current_language);
     96  1.1  christos 
     97  1.1  christos   if (emit_stop_event (bs, stop_signal) < 0)
     98  1.1  christos     gdbpy_print_stack ();
     99  1.1  christos 
    100  1.1  christos   do_cleanups (cleanup);
    101  1.1  christos }
    102  1.1  christos 
    103  1.1  christos static void
    104  1.1  christos python_on_resume (ptid_t ptid)
    105  1.1  christos {
    106  1.1  christos   struct cleanup *cleanup;
    107  1.1  christos 
    108  1.1  christos   if (!gdb_python_initialized)
    109  1.1  christos     return;
    110  1.1  christos 
    111  1.1  christos   cleanup = ensure_python_env (target_gdbarch (), current_language);
    112  1.1  christos 
    113  1.1  christos   if (emit_continue_event (ptid) < 0)
    114  1.1  christos     gdbpy_print_stack ();
    115  1.1  christos 
    116  1.1  christos   do_cleanups (cleanup);
    117  1.1  christos }
    118  1.1  christos 
    119  1.3  christos /* Callback, registered as an observer, that notifies Python listeners
    120  1.3  christos    when an inferior function call is about to be made. */
    121  1.3  christos 
    122  1.3  christos static void
    123  1.3  christos python_on_inferior_call_pre (ptid_t thread, CORE_ADDR address)
    124  1.3  christos {
    125  1.3  christos   struct cleanup *cleanup;
    126  1.3  christos 
    127  1.3  christos   cleanup = ensure_python_env (target_gdbarch (), current_language);
    128  1.3  christos 
    129  1.3  christos   if (emit_inferior_call_event (INFERIOR_CALL_PRE, thread, address) < 0)
    130  1.3  christos     gdbpy_print_stack ();
    131  1.3  christos 
    132  1.3  christos   do_cleanups (cleanup);
    133  1.3  christos }
    134  1.3  christos 
    135  1.3  christos /* Callback, registered as an observer, that notifies Python listeners
    136  1.3  christos    when an inferior function call has completed. */
    137  1.3  christos 
    138  1.3  christos static void
    139  1.3  christos python_on_inferior_call_post (ptid_t thread, CORE_ADDR address)
    140  1.3  christos {
    141  1.3  christos   struct cleanup *cleanup;
    142  1.3  christos 
    143  1.3  christos   cleanup = ensure_python_env (target_gdbarch (), current_language);
    144  1.3  christos 
    145  1.3  christos   if (emit_inferior_call_event (INFERIOR_CALL_POST, thread, address) < 0)
    146  1.3  christos     gdbpy_print_stack ();
    147  1.3  christos 
    148  1.3  christos   do_cleanups (cleanup);
    149  1.3  christos }
    150  1.3  christos 
    151  1.3  christos /* Callback, registered as an observer, that notifies Python listeners
    152  1.3  christos    when a part of memory has been modified by user action (eg via a
    153  1.3  christos    'set' command). */
    154  1.3  christos 
    155  1.3  christos static void
    156  1.3  christos python_on_memory_change (struct inferior *inferior, CORE_ADDR addr, ssize_t len, const bfd_byte *data)
    157  1.3  christos {
    158  1.3  christos   struct cleanup *cleanup;
    159  1.3  christos 
    160  1.3  christos   cleanup = ensure_python_env (target_gdbarch (), current_language);
    161  1.3  christos 
    162  1.3  christos   if (emit_memory_changed_event (addr, len) < 0)
    163  1.3  christos     gdbpy_print_stack ();
    164  1.3  christos 
    165  1.3  christos   do_cleanups (cleanup);
    166  1.3  christos }
    167  1.3  christos 
    168  1.3  christos /* Callback, registered as an observer, that notifies Python listeners
    169  1.3  christos    when a register has been modified by user action (eg via a 'set'
    170  1.3  christos    command). */
    171  1.3  christos 
    172  1.3  christos static void
    173  1.3  christos python_on_register_change (struct frame_info *frame, int regnum)
    174  1.3  christos {
    175  1.3  christos   struct cleanup *cleanup;
    176  1.3  christos 
    177  1.3  christos   cleanup = ensure_python_env (target_gdbarch (), current_language);
    178  1.3  christos 
    179  1.3  christos   if (emit_register_changed_event (frame, regnum) < 0)
    180  1.3  christos     gdbpy_print_stack ();
    181  1.3  christos 
    182  1.3  christos   do_cleanups (cleanup);
    183  1.3  christos }
    184  1.3  christos 
    185  1.1  christos static void
    186  1.1  christos python_inferior_exit (struct inferior *inf)
    187  1.1  christos {
    188  1.1  christos   struct cleanup *cleanup;
    189  1.1  christos   const LONGEST *exit_code = NULL;
    190  1.1  christos 
    191  1.1  christos   if (!gdb_python_initialized)
    192  1.1  christos     return;
    193  1.1  christos 
    194  1.1  christos   cleanup = ensure_python_env (target_gdbarch (), current_language);
    195  1.1  christos 
    196  1.1  christos   if (inf->has_exit_code)
    197  1.1  christos     exit_code = &inf->exit_code;
    198  1.1  christos 
    199  1.1  christos   if (emit_exited_event (exit_code, inf) < 0)
    200  1.1  christos     gdbpy_print_stack ();
    201  1.1  christos 
    202  1.1  christos   do_cleanups (cleanup);
    203  1.1  christos }
    204  1.1  christos 
    205  1.1  christos /* Callback used to notify Python listeners about new objfiles loaded in the
    206  1.3  christos    inferior.  OBJFILE may be NULL which means that the objfile list has been
    207  1.3  christos    cleared (emptied).  */
    208  1.1  christos 
    209  1.1  christos static void
    210  1.1  christos python_new_objfile (struct objfile *objfile)
    211  1.1  christos {
    212  1.1  christos   struct cleanup *cleanup;
    213  1.1  christos 
    214  1.1  christos   if (!gdb_python_initialized)
    215  1.1  christos     return;
    216  1.1  christos 
    217  1.3  christos   cleanup = ensure_python_env (objfile != NULL
    218  1.3  christos 			       ? get_objfile_arch (objfile)
    219  1.3  christos 			       : target_gdbarch (),
    220  1.3  christos 			       current_language);
    221  1.1  christos 
    222  1.3  christos   if (objfile == NULL)
    223  1.3  christos     {
    224  1.3  christos       if (emit_clear_objfiles_event () < 0)
    225  1.3  christos 	gdbpy_print_stack ();
    226  1.3  christos     }
    227  1.3  christos   else
    228  1.3  christos     {
    229  1.3  christos       if (emit_new_objfile_event (objfile) < 0)
    230  1.3  christos 	gdbpy_print_stack ();
    231  1.3  christos     }
    232  1.1  christos 
    233  1.1  christos   do_cleanups (cleanup);
    234  1.1  christos }
    235  1.1  christos 
    236  1.1  christos /* Return a reference to the Python object of type Inferior
    237  1.1  christos    representing INFERIOR.  If the object has already been created,
    238  1.1  christos    return it and increment the reference count,  otherwise, create it.
    239  1.1  christos    Return NULL on failure.  */
    240  1.1  christos PyObject *
    241  1.1  christos inferior_to_inferior_object (struct inferior *inferior)
    242  1.1  christos {
    243  1.1  christos   inferior_object *inf_obj;
    244  1.1  christos 
    245  1.6  christos   inf_obj = (inferior_object *) inferior_data (inferior, infpy_inf_data_key);
    246  1.1  christos   if (!inf_obj)
    247  1.1  christos     {
    248  1.1  christos       inf_obj = PyObject_New (inferior_object, &inferior_object_type);
    249  1.1  christos       if (!inf_obj)
    250  1.1  christos 	  return NULL;
    251  1.1  christos 
    252  1.1  christos       inf_obj->inferior = inferior;
    253  1.1  christos       inf_obj->threads = NULL;
    254  1.1  christos       inf_obj->nthreads = 0;
    255  1.1  christos 
    256  1.1  christos       set_inferior_data (inferior, infpy_inf_data_key, inf_obj);
    257  1.1  christos 
    258  1.1  christos     }
    259  1.1  christos   else
    260  1.1  christos     Py_INCREF ((PyObject *)inf_obj);
    261  1.1  christos 
    262  1.1  christos   return (PyObject *) inf_obj;
    263  1.1  christos }
    264  1.1  christos 
    265  1.1  christos /* Finds the Python Inferior object for the given PID.  Returns a
    266  1.1  christos    reference, or NULL if PID does not match any inferior object. */
    267  1.1  christos 
    268  1.1  christos PyObject *
    269  1.1  christos find_inferior_object (int pid)
    270  1.1  christos {
    271  1.1  christos   struct inferior *inf = find_inferior_pid (pid);
    272  1.1  christos 
    273  1.1  christos   if (inf)
    274  1.1  christos     return inferior_to_inferior_object (inf);
    275  1.1  christos 
    276  1.1  christos   return NULL;
    277  1.1  christos }
    278  1.1  christos 
    279  1.1  christos thread_object *
    280  1.1  christos find_thread_object (ptid_t ptid)
    281  1.1  christos {
    282  1.1  christos   int pid;
    283  1.1  christos   struct threadlist_entry *thread;
    284  1.1  christos   PyObject *inf_obj;
    285  1.1  christos   thread_object *found = NULL;
    286  1.1  christos 
    287  1.1  christos   pid = ptid_get_pid (ptid);
    288  1.1  christos   if (pid == 0)
    289  1.1  christos     return NULL;
    290  1.1  christos 
    291  1.1  christos   inf_obj = find_inferior_object (pid);
    292  1.1  christos 
    293  1.1  christos   if (! inf_obj)
    294  1.1  christos     return NULL;
    295  1.1  christos 
    296  1.1  christos   for (thread = ((inferior_object *)inf_obj)->threads; thread;
    297  1.1  christos        thread = thread->next)
    298  1.1  christos     if (ptid_equal (thread->thread_obj->thread->ptid, ptid))
    299  1.1  christos       {
    300  1.1  christos 	found = thread->thread_obj;
    301  1.1  christos 	break;
    302  1.1  christos       }
    303  1.1  christos 
    304  1.1  christos   Py_DECREF (inf_obj);
    305  1.1  christos 
    306  1.1  christos   if (found)
    307  1.1  christos     return found;
    308  1.1  christos 
    309  1.1  christos   return NULL;
    310  1.1  christos }
    311  1.1  christos 
    312  1.1  christos static void
    313  1.1  christos add_thread_object (struct thread_info *tp)
    314  1.1  christos {
    315  1.1  christos   struct cleanup *cleanup;
    316  1.1  christos   thread_object *thread_obj;
    317  1.1  christos   inferior_object *inf_obj;
    318  1.1  christos   struct threadlist_entry *entry;
    319  1.1  christos 
    320  1.1  christos   if (!gdb_python_initialized)
    321  1.1  christos     return;
    322  1.1  christos 
    323  1.1  christos   cleanup = ensure_python_env (python_gdbarch, python_language);
    324  1.1  christos 
    325  1.1  christos   thread_obj = create_thread_object (tp);
    326  1.1  christos   if (!thread_obj)
    327  1.1  christos     {
    328  1.1  christos       gdbpy_print_stack ();
    329  1.1  christos       do_cleanups (cleanup);
    330  1.1  christos       return;
    331  1.1  christos     }
    332  1.1  christos 
    333  1.1  christos   inf_obj = (inferior_object *) thread_obj->inf_obj;
    334  1.1  christos 
    335  1.6  christos   entry = XNEW (struct threadlist_entry);
    336  1.1  christos   entry->thread_obj = thread_obj;
    337  1.1  christos   entry->next = inf_obj->threads;
    338  1.1  christos 
    339  1.1  christos   inf_obj->threads = entry;
    340  1.1  christos   inf_obj->nthreads++;
    341  1.1  christos 
    342  1.1  christos   do_cleanups (cleanup);
    343  1.1  christos }
    344  1.1  christos 
    345  1.1  christos static void
    346  1.1  christos delete_thread_object (struct thread_info *tp, int ignore)
    347  1.1  christos {
    348  1.1  christos   struct cleanup *cleanup;
    349  1.1  christos   inferior_object *inf_obj;
    350  1.1  christos   struct threadlist_entry **entry, *tmp;
    351  1.1  christos 
    352  1.1  christos   if (!gdb_python_initialized)
    353  1.1  christos     return;
    354  1.1  christos 
    355  1.1  christos   cleanup = ensure_python_env (python_gdbarch, python_language);
    356  1.1  christos 
    357  1.1  christos   inf_obj
    358  1.1  christos     = (inferior_object *) find_inferior_object (ptid_get_pid (tp->ptid));
    359  1.1  christos   if (!inf_obj)
    360  1.1  christos     {
    361  1.1  christos       do_cleanups (cleanup);
    362  1.1  christos       return;
    363  1.1  christos     }
    364  1.1  christos 
    365  1.1  christos   /* Find thread entry in its inferior's thread_list.  */
    366  1.1  christos   for (entry = &inf_obj->threads; *entry != NULL; entry =
    367  1.1  christos 	 &(*entry)->next)
    368  1.1  christos     if ((*entry)->thread_obj->thread == tp)
    369  1.1  christos       break;
    370  1.1  christos 
    371  1.1  christos   if (!*entry)
    372  1.1  christos     {
    373  1.1  christos       Py_DECREF (inf_obj);
    374  1.1  christos       do_cleanups (cleanup);
    375  1.1  christos       return;
    376  1.1  christos     }
    377  1.1  christos 
    378  1.1  christos   tmp = *entry;
    379  1.1  christos   tmp->thread_obj->thread = NULL;
    380  1.1  christos 
    381  1.1  christos   *entry = (*entry)->next;
    382  1.1  christos   inf_obj->nthreads--;
    383  1.1  christos 
    384  1.1  christos   Py_DECREF (tmp->thread_obj);
    385  1.1  christos   Py_DECREF (inf_obj);
    386  1.1  christos   xfree (tmp);
    387  1.1  christos 
    388  1.1  christos   do_cleanups (cleanup);
    389  1.1  christos }
    390  1.1  christos 
    391  1.1  christos static PyObject *
    392  1.1  christos infpy_threads (PyObject *self, PyObject *args)
    393  1.1  christos {
    394  1.1  christos   int i;
    395  1.1  christos   struct threadlist_entry *entry;
    396  1.1  christos   inferior_object *inf_obj = (inferior_object *) self;
    397  1.1  christos   PyObject *tuple;
    398  1.1  christos 
    399  1.1  christos   INFPY_REQUIRE_VALID (inf_obj);
    400  1.1  christos 
    401  1.5  christos   TRY
    402  1.5  christos     {
    403  1.5  christos       update_thread_list ();
    404  1.5  christos     }
    405  1.5  christos   CATCH (except, RETURN_MASK_ALL)
    406  1.5  christos     {
    407  1.5  christos       GDB_PY_HANDLE_EXCEPTION (except);
    408  1.5  christos     }
    409  1.5  christos   END_CATCH
    410  1.1  christos 
    411  1.1  christos   tuple = PyTuple_New (inf_obj->nthreads);
    412  1.1  christos   if (!tuple)
    413  1.1  christos     return NULL;
    414  1.1  christos 
    415  1.1  christos   for (i = 0, entry = inf_obj->threads; i < inf_obj->nthreads;
    416  1.1  christos        i++, entry = entry->next)
    417  1.1  christos     {
    418  1.1  christos       Py_INCREF (entry->thread_obj);
    419  1.1  christos       PyTuple_SET_ITEM (tuple, i, (PyObject *) entry->thread_obj);
    420  1.1  christos     }
    421  1.1  christos 
    422  1.1  christos   return tuple;
    423  1.1  christos }
    424  1.1  christos 
    425  1.1  christos static PyObject *
    426  1.1  christos infpy_get_num (PyObject *self, void *closure)
    427  1.1  christos {
    428  1.1  christos   inferior_object *inf = (inferior_object *) self;
    429  1.1  christos 
    430  1.1  christos   INFPY_REQUIRE_VALID (inf);
    431  1.1  christos 
    432  1.1  christos   return PyLong_FromLong (inf->inferior->num);
    433  1.1  christos }
    434  1.1  christos 
    435  1.1  christos static PyObject *
    436  1.1  christos infpy_get_pid (PyObject *self, void *closure)
    437  1.1  christos {
    438  1.1  christos   inferior_object *inf = (inferior_object *) self;
    439  1.1  christos 
    440  1.1  christos   INFPY_REQUIRE_VALID (inf);
    441  1.1  christos 
    442  1.1  christos   return PyLong_FromLong (inf->inferior->pid);
    443  1.1  christos }
    444  1.1  christos 
    445  1.1  christos static PyObject *
    446  1.1  christos infpy_get_was_attached (PyObject *self, void *closure)
    447  1.1  christos {
    448  1.1  christos   inferior_object *inf = (inferior_object *) self;
    449  1.1  christos 
    450  1.1  christos   INFPY_REQUIRE_VALID (inf);
    451  1.1  christos   if (inf->inferior->attach_flag)
    452  1.1  christos     Py_RETURN_TRUE;
    453  1.1  christos   Py_RETURN_FALSE;
    454  1.1  christos }
    455  1.1  christos 
    456  1.1  christos static int
    457  1.1  christos build_inferior_list (struct inferior *inf, void *arg)
    458  1.1  christos {
    459  1.6  christos   PyObject *list = (PyObject *) arg;
    460  1.1  christos   PyObject *inferior = inferior_to_inferior_object (inf);
    461  1.1  christos   int success = 0;
    462  1.1  christos 
    463  1.1  christos   if (! inferior)
    464  1.1  christos     return 0;
    465  1.1  christos 
    466  1.1  christos   success = PyList_Append (list, inferior);
    467  1.1  christos   Py_DECREF (inferior);
    468  1.1  christos 
    469  1.1  christos   if (success)
    470  1.1  christos     return 1;
    471  1.1  christos 
    472  1.1  christos   return 0;
    473  1.1  christos }
    474  1.1  christos 
    475  1.1  christos /* Implementation of gdb.inferiors () -> (gdb.Inferior, ...).
    476  1.1  christos    Returns a tuple of all inferiors.  */
    477  1.1  christos PyObject *
    478  1.1  christos gdbpy_inferiors (PyObject *unused, PyObject *unused2)
    479  1.1  christos {
    480  1.1  christos   PyObject *list, *tuple;
    481  1.1  christos 
    482  1.1  christos   list = PyList_New (0);
    483  1.1  christos   if (!list)
    484  1.1  christos     return NULL;
    485  1.1  christos 
    486  1.1  christos   if (iterate_over_inferiors (build_inferior_list, list))
    487  1.1  christos     {
    488  1.1  christos       Py_DECREF (list);
    489  1.1  christos       return NULL;
    490  1.1  christos     }
    491  1.1  christos 
    492  1.1  christos   tuple = PyList_AsTuple (list);
    493  1.1  christos   Py_DECREF (list);
    494  1.1  christos 
    495  1.1  christos   return tuple;
    496  1.1  christos }
    497  1.1  christos 
    498  1.1  christos /* Membuf and memory manipulation.  */
    499  1.1  christos 
    500  1.1  christos /* Implementation of Inferior.read_memory (address, length).
    501  1.1  christos    Returns a Python buffer object with LENGTH bytes of the inferior's
    502  1.1  christos    memory at ADDRESS.  Both arguments are integers.  Returns NULL on error,
    503  1.1  christos    with a python exception set.  */
    504  1.1  christos static PyObject *
    505  1.1  christos infpy_read_memory (PyObject *self, PyObject *args, PyObject *kw)
    506  1.1  christos {
    507  1.1  christos   CORE_ADDR addr, length;
    508  1.6  christos   gdb_byte *buffer = NULL;
    509  1.1  christos   membuf_object *membuf_obj;
    510  1.1  christos   PyObject *addr_obj, *length_obj, *result;
    511  1.1  christos   static char *keywords[] = { "address", "length", NULL };
    512  1.1  christos 
    513  1.1  christos   if (! PyArg_ParseTupleAndKeywords (args, kw, "OO", keywords,
    514  1.1  christos 				     &addr_obj, &length_obj))
    515  1.1  christos     return NULL;
    516  1.1  christos 
    517  1.1  christos   if (get_addr_from_python (addr_obj, &addr) < 0
    518  1.1  christos       || get_addr_from_python (length_obj, &length) < 0)
    519  1.1  christos     return NULL;
    520  1.1  christos 
    521  1.5  christos   TRY
    522  1.1  christos     {
    523  1.6  christos       buffer = (gdb_byte *) xmalloc (length);
    524  1.1  christos 
    525  1.1  christos       read_memory (addr, buffer, length);
    526  1.1  christos     }
    527  1.5  christos   CATCH (except, RETURN_MASK_ALL)
    528  1.1  christos     {
    529  1.1  christos       xfree (buffer);
    530  1.1  christos       GDB_PY_HANDLE_EXCEPTION (except);
    531  1.1  christos     }
    532  1.5  christos   END_CATCH
    533  1.1  christos 
    534  1.1  christos   membuf_obj = PyObject_New (membuf_object, &membuf_object_type);
    535  1.1  christos   if (membuf_obj == NULL)
    536  1.1  christos     {
    537  1.1  christos       xfree (buffer);
    538  1.1  christos       return NULL;
    539  1.1  christos     }
    540  1.1  christos 
    541  1.1  christos   membuf_obj->buffer = buffer;
    542  1.1  christos   membuf_obj->addr = addr;
    543  1.1  christos   membuf_obj->length = length;
    544  1.1  christos 
    545  1.1  christos #ifdef IS_PY3K
    546  1.1  christos   result = PyMemoryView_FromObject ((PyObject *) membuf_obj);
    547  1.1  christos #else
    548  1.1  christos   result = PyBuffer_FromReadWriteObject ((PyObject *) membuf_obj, 0,
    549  1.1  christos 					 Py_END_OF_BUFFER);
    550  1.1  christos #endif
    551  1.1  christos   Py_DECREF (membuf_obj);
    552  1.1  christos 
    553  1.1  christos   return result;
    554  1.1  christos }
    555  1.1  christos 
    556  1.1  christos /* Implementation of Inferior.write_memory (address, buffer [, length]).
    557  1.1  christos    Writes the contents of BUFFER (a Python object supporting the read
    558  1.1  christos    buffer protocol) at ADDRESS in the inferior's memory.  Write LENGTH
    559  1.1  christos    bytes from BUFFER, or its entire contents if the argument is not
    560  1.1  christos    provided.  The function returns nothing.  Returns NULL on error, with
    561  1.1  christos    a python exception set.  */
    562  1.1  christos static PyObject *
    563  1.1  christos infpy_write_memory (PyObject *self, PyObject *args, PyObject *kw)
    564  1.1  christos {
    565  1.5  christos   struct gdb_exception except = exception_none;
    566  1.1  christos   Py_ssize_t buf_len;
    567  1.6  christos   const gdb_byte *buffer;
    568  1.1  christos   CORE_ADDR addr, length;
    569  1.1  christos   PyObject *addr_obj, *length_obj = NULL;
    570  1.1  christos   static char *keywords[] = { "address", "buffer", "length", NULL };
    571  1.1  christos #ifdef IS_PY3K
    572  1.1  christos   Py_buffer pybuf;
    573  1.1  christos 
    574  1.1  christos   if (! PyArg_ParseTupleAndKeywords (args, kw, "Os*|O", keywords,
    575  1.1  christos 				     &addr_obj, &pybuf,
    576  1.1  christos 				     &length_obj))
    577  1.1  christos     return NULL;
    578  1.1  christos 
    579  1.6  christos   buffer = (const gdb_byte *) pybuf.buf;
    580  1.1  christos   buf_len = pybuf.len;
    581  1.1  christos #else
    582  1.1  christos   if (! PyArg_ParseTupleAndKeywords (args, kw, "Os#|O", keywords,
    583  1.1  christos 				     &addr_obj, &buffer, &buf_len,
    584  1.1  christos 				     &length_obj))
    585  1.1  christos     return NULL;
    586  1.6  christos 
    587  1.6  christos   buffer = (const gdb_byte *) buffer;
    588  1.1  christos #endif
    589  1.1  christos 
    590  1.1  christos   if (get_addr_from_python (addr_obj, &addr) < 0)
    591  1.1  christos     goto fail;
    592  1.1  christos 
    593  1.1  christos   if (!length_obj)
    594  1.1  christos     length = buf_len;
    595  1.1  christos   else if (get_addr_from_python (length_obj, &length) < 0)
    596  1.1  christos     goto fail;
    597  1.1  christos 
    598  1.5  christos   TRY
    599  1.1  christos     {
    600  1.6  christos       write_memory_with_notification (addr, buffer, length);
    601  1.1  christos     }
    602  1.5  christos   CATCH (ex, RETURN_MASK_ALL)
    603  1.5  christos     {
    604  1.5  christos       except = ex;
    605  1.5  christos     }
    606  1.5  christos   END_CATCH
    607  1.5  christos 
    608  1.1  christos #ifdef IS_PY3K
    609  1.1  christos   PyBuffer_Release (&pybuf);
    610  1.1  christos #endif
    611  1.1  christos   GDB_PY_HANDLE_EXCEPTION (except);
    612  1.1  christos 
    613  1.1  christos   Py_RETURN_NONE;
    614  1.1  christos 
    615  1.1  christos  fail:
    616  1.1  christos #ifdef IS_PY3K
    617  1.1  christos   PyBuffer_Release (&pybuf);
    618  1.1  christos #endif
    619  1.1  christos   return NULL;
    620  1.1  christos }
    621  1.1  christos 
    622  1.1  christos /* Destructor of Membuf objects.  */
    623  1.1  christos static void
    624  1.1  christos mbpy_dealloc (PyObject *self)
    625  1.1  christos {
    626  1.1  christos   xfree (((membuf_object *) self)->buffer);
    627  1.1  christos   Py_TYPE (self)->tp_free (self);
    628  1.1  christos }
    629  1.1  christos 
    630  1.1  christos /* Return a description of the Membuf object.  */
    631  1.1  christos static PyObject *
    632  1.1  christos mbpy_str (PyObject *self)
    633  1.1  christos {
    634  1.1  christos   membuf_object *membuf_obj = (membuf_object *) self;
    635  1.1  christos 
    636  1.1  christos   return PyString_FromFormat (_("Memory buffer for address %s, \
    637  1.1  christos which is %s bytes long."),
    638  1.1  christos 			      paddress (python_gdbarch, membuf_obj->addr),
    639  1.1  christos 			      pulongest (membuf_obj->length));
    640  1.1  christos }
    641  1.1  christos 
    642  1.1  christos #ifdef IS_PY3K
    643  1.1  christos 
    644  1.1  christos static int
    645  1.1  christos get_buffer (PyObject *self, Py_buffer *buf, int flags)
    646  1.1  christos {
    647  1.1  christos   membuf_object *membuf_obj = (membuf_object *) self;
    648  1.1  christos   int ret;
    649  1.1  christos 
    650  1.1  christos   ret = PyBuffer_FillInfo (buf, self, membuf_obj->buffer,
    651  1.1  christos 			   membuf_obj->length, 0,
    652  1.1  christos 			   PyBUF_CONTIG);
    653  1.1  christos   buf->format = "c";
    654  1.1  christos 
    655  1.1  christos   return ret;
    656  1.1  christos }
    657  1.1  christos 
    658  1.1  christos #else
    659  1.1  christos 
    660  1.1  christos static Py_ssize_t
    661  1.1  christos get_read_buffer (PyObject *self, Py_ssize_t segment, void **ptrptr)
    662  1.1  christos {
    663  1.1  christos   membuf_object *membuf_obj = (membuf_object *) self;
    664  1.1  christos 
    665  1.1  christos   if (segment)
    666  1.1  christos     {
    667  1.1  christos       PyErr_SetString (PyExc_SystemError,
    668  1.1  christos 		       _("The memory buffer supports only one segment."));
    669  1.1  christos       return -1;
    670  1.1  christos     }
    671  1.1  christos 
    672  1.1  christos   *ptrptr = membuf_obj->buffer;
    673  1.1  christos 
    674  1.1  christos   return membuf_obj->length;
    675  1.1  christos }
    676  1.1  christos 
    677  1.1  christos static Py_ssize_t
    678  1.1  christos get_write_buffer (PyObject *self, Py_ssize_t segment, void **ptrptr)
    679  1.1  christos {
    680  1.1  christos   return get_read_buffer (self, segment, ptrptr);
    681  1.1  christos }
    682  1.1  christos 
    683  1.1  christos static Py_ssize_t
    684  1.1  christos get_seg_count (PyObject *self, Py_ssize_t *lenp)
    685  1.1  christos {
    686  1.1  christos   if (lenp)
    687  1.1  christos     *lenp = ((membuf_object *) self)->length;
    688  1.1  christos 
    689  1.1  christos   return 1;
    690  1.1  christos }
    691  1.1  christos 
    692  1.1  christos static Py_ssize_t
    693  1.1  christos get_char_buffer (PyObject *self, Py_ssize_t segment, char **ptrptr)
    694  1.1  christos {
    695  1.1  christos   void *ptr = NULL;
    696  1.1  christos   Py_ssize_t ret;
    697  1.1  christos 
    698  1.1  christos   ret = get_read_buffer (self, segment, &ptr);
    699  1.1  christos   *ptrptr = (char *) ptr;
    700  1.1  christos 
    701  1.1  christos   return ret;
    702  1.1  christos }
    703  1.1  christos 
    704  1.1  christos #endif	/* IS_PY3K */
    705  1.1  christos 
    706  1.1  christos /* Implementation of
    707  1.1  christos    gdb.search_memory (address, length, pattern).  ADDRESS is the
    708  1.1  christos    address to start the search.  LENGTH specifies the scope of the
    709  1.1  christos    search from ADDRESS.  PATTERN is the pattern to search for (and
    710  1.1  christos    must be a Python object supporting the buffer protocol).
    711  1.1  christos    Returns a Python Long object holding the address where the pattern
    712  1.1  christos    was located, or if the pattern was not found, returns None.  Returns NULL
    713  1.1  christos    on error, with a python exception set.  */
    714  1.1  christos static PyObject *
    715  1.1  christos infpy_search_memory (PyObject *self, PyObject *args, PyObject *kw)
    716  1.1  christos {
    717  1.5  christos   struct gdb_exception except = exception_none;
    718  1.1  christos   CORE_ADDR start_addr, length;
    719  1.1  christos   static char *keywords[] = { "address", "length", "pattern", NULL };
    720  1.1  christos   PyObject *start_addr_obj, *length_obj;
    721  1.1  christos   Py_ssize_t pattern_size;
    722  1.6  christos   const gdb_byte *buffer;
    723  1.1  christos   CORE_ADDR found_addr;
    724  1.1  christos   int found = 0;
    725  1.1  christos #ifdef IS_PY3K
    726  1.1  christos   Py_buffer pybuf;
    727  1.1  christos 
    728  1.1  christos   if (! PyArg_ParseTupleAndKeywords (args, kw, "OOs*", keywords,
    729  1.1  christos 				     &start_addr_obj, &length_obj,
    730  1.1  christos 				     &pybuf))
    731  1.1  christos     return NULL;
    732  1.1  christos 
    733  1.6  christos   buffer = (const gdb_byte *) pybuf.buf;
    734  1.1  christos   pattern_size = pybuf.len;
    735  1.1  christos #else
    736  1.1  christos   PyObject *pattern;
    737  1.6  christos   const void *vbuffer;
    738  1.1  christos 
    739  1.1  christos   if (! PyArg_ParseTupleAndKeywords (args, kw, "OOO", keywords,
    740  1.1  christos  				     &start_addr_obj, &length_obj,
    741  1.1  christos 				     &pattern))
    742  1.1  christos      return NULL;
    743  1.1  christos 
    744  1.1  christos   if (!PyObject_CheckReadBuffer (pattern))
    745  1.1  christos     {
    746  1.1  christos       PyErr_SetString (PyExc_RuntimeError,
    747  1.1  christos 		       _("The pattern is not a Python buffer."));
    748  1.1  christos 
    749  1.1  christos       return NULL;
    750  1.1  christos     }
    751  1.1  christos 
    752  1.6  christos   if (PyObject_AsReadBuffer (pattern, &vbuffer, &pattern_size) == -1)
    753  1.1  christos     return NULL;
    754  1.6  christos 
    755  1.6  christos   buffer = (const gdb_byte *) vbuffer;
    756  1.1  christos #endif
    757  1.1  christos 
    758  1.1  christos   if (get_addr_from_python (start_addr_obj, &start_addr) < 0)
    759  1.1  christos     goto fail;
    760  1.1  christos 
    761  1.1  christos   if (get_addr_from_python (length_obj, &length) < 0)
    762  1.1  christos     goto fail;
    763  1.1  christos 
    764  1.1  christos   if (!length)
    765  1.1  christos     {
    766  1.1  christos       PyErr_SetString (PyExc_ValueError,
    767  1.1  christos 		       _("Search range is empty."));
    768  1.1  christos       goto fail;
    769  1.1  christos     }
    770  1.1  christos   /* Watch for overflows.  */
    771  1.1  christos   else if (length > CORE_ADDR_MAX
    772  1.1  christos 	   || (start_addr + length - 1) < start_addr)
    773  1.1  christos     {
    774  1.1  christos       PyErr_SetString (PyExc_ValueError,
    775  1.1  christos 		       _("The search range is too large."));
    776  1.1  christos       goto fail;
    777  1.1  christos     }
    778  1.1  christos 
    779  1.5  christos   TRY
    780  1.1  christos     {
    781  1.1  christos       found = target_search_memory (start_addr, length,
    782  1.1  christos 				    buffer, pattern_size,
    783  1.1  christos 				    &found_addr);
    784  1.1  christos     }
    785  1.5  christos   CATCH (ex, RETURN_MASK_ALL)
    786  1.5  christos     {
    787  1.5  christos       except = ex;
    788  1.5  christos     }
    789  1.5  christos   END_CATCH
    790  1.5  christos 
    791  1.1  christos #ifdef IS_PY3K
    792  1.1  christos   PyBuffer_Release (&pybuf);
    793  1.1  christos #endif
    794  1.1  christos   GDB_PY_HANDLE_EXCEPTION (except);
    795  1.1  christos 
    796  1.1  christos   if (found)
    797  1.1  christos     return PyLong_FromLong (found_addr);
    798  1.1  christos   else
    799  1.1  christos     Py_RETURN_NONE;
    800  1.1  christos 
    801  1.1  christos  fail:
    802  1.1  christos #ifdef IS_PY3K
    803  1.1  christos   PyBuffer_Release (&pybuf);
    804  1.1  christos #endif
    805  1.1  christos   return NULL;
    806  1.1  christos }
    807  1.1  christos 
    808  1.1  christos /* Implementation of gdb.Inferior.is_valid (self) -> Boolean.
    809  1.1  christos    Returns True if this inferior object still exists in GDB.  */
    810  1.1  christos 
    811  1.1  christos static PyObject *
    812  1.1  christos infpy_is_valid (PyObject *self, PyObject *args)
    813  1.1  christos {
    814  1.1  christos   inferior_object *inf = (inferior_object *) self;
    815  1.1  christos 
    816  1.1  christos   if (! inf->inferior)
    817  1.1  christos     Py_RETURN_FALSE;
    818  1.1  christos 
    819  1.1  christos   Py_RETURN_TRUE;
    820  1.1  christos }
    821  1.1  christos 
    822  1.1  christos static void
    823  1.1  christos infpy_dealloc (PyObject *obj)
    824  1.1  christos {
    825  1.1  christos   inferior_object *inf_obj = (inferior_object *) obj;
    826  1.1  christos   struct inferior *inf = inf_obj->inferior;
    827  1.1  christos 
    828  1.1  christos   if (! inf)
    829  1.1  christos     return;
    830  1.1  christos 
    831  1.1  christos   set_inferior_data (inf, infpy_inf_data_key, NULL);
    832  1.1  christos }
    833  1.1  christos 
    834  1.1  christos /* Clear the INFERIOR pointer in an Inferior object and clear the
    835  1.1  christos    thread list.  */
    836  1.1  christos static void
    837  1.1  christos py_free_inferior (struct inferior *inf, void *datum)
    838  1.1  christos {
    839  1.1  christos 
    840  1.1  christos   struct cleanup *cleanup;
    841  1.6  christos   inferior_object *inf_obj = (inferior_object *) datum;
    842  1.1  christos   struct threadlist_entry *th_entry, *th_tmp;
    843  1.1  christos 
    844  1.1  christos   if (!gdb_python_initialized)
    845  1.1  christos     return;
    846  1.1  christos 
    847  1.1  christos   cleanup = ensure_python_env (python_gdbarch, python_language);
    848  1.1  christos 
    849  1.1  christos   inf_obj->inferior = NULL;
    850  1.1  christos 
    851  1.1  christos   /* Deallocate threads list.  */
    852  1.1  christos   for (th_entry = inf_obj->threads; th_entry != NULL;)
    853  1.1  christos     {
    854  1.1  christos       Py_DECREF (th_entry->thread_obj);
    855  1.1  christos 
    856  1.1  christos       th_tmp = th_entry;
    857  1.1  christos       th_entry = th_entry->next;
    858  1.1  christos       xfree (th_tmp);
    859  1.1  christos     }
    860  1.1  christos 
    861  1.1  christos   inf_obj->nthreads = 0;
    862  1.1  christos 
    863  1.1  christos   Py_DECREF ((PyObject *) inf_obj);
    864  1.1  christos   do_cleanups (cleanup);
    865  1.1  christos }
    866  1.1  christos 
    867  1.1  christos /* Implementation of gdb.selected_inferior() -> gdb.Inferior.
    868  1.1  christos    Returns the current inferior object.  */
    869  1.1  christos 
    870  1.1  christos PyObject *
    871  1.1  christos gdbpy_selected_inferior (PyObject *self, PyObject *args)
    872  1.1  christos {
    873  1.1  christos   return inferior_to_inferior_object (current_inferior ());
    874  1.1  christos }
    875  1.1  christos 
    876  1.1  christos int
    877  1.1  christos gdbpy_initialize_inferior (void)
    878  1.1  christos {
    879  1.1  christos   if (PyType_Ready (&inferior_object_type) < 0)
    880  1.1  christos     return -1;
    881  1.1  christos 
    882  1.1  christos   if (gdb_pymodule_addobject (gdb_module, "Inferior",
    883  1.1  christos 			      (PyObject *) &inferior_object_type) < 0)
    884  1.1  christos     return -1;
    885  1.1  christos 
    886  1.1  christos   infpy_inf_data_key =
    887  1.1  christos     register_inferior_data_with_cleanup (NULL, py_free_inferior);
    888  1.1  christos 
    889  1.1  christos   observer_attach_new_thread (add_thread_object);
    890  1.1  christos   observer_attach_thread_exit (delete_thread_object);
    891  1.1  christos   observer_attach_normal_stop (python_on_normal_stop);
    892  1.1  christos   observer_attach_target_resumed (python_on_resume);
    893  1.3  christos   observer_attach_inferior_call_pre (python_on_inferior_call_pre);
    894  1.3  christos   observer_attach_inferior_call_post (python_on_inferior_call_post);
    895  1.3  christos   observer_attach_memory_changed (python_on_memory_change);
    896  1.3  christos   observer_attach_register_changed (python_on_register_change);
    897  1.1  christos   observer_attach_inferior_exit (python_inferior_exit);
    898  1.1  christos   observer_attach_new_objfile (python_new_objfile);
    899  1.1  christos 
    900  1.1  christos   membuf_object_type.tp_new = PyType_GenericNew;
    901  1.1  christos   if (PyType_Ready (&membuf_object_type) < 0)
    902  1.1  christos     return -1;
    903  1.1  christos 
    904  1.1  christos   return gdb_pymodule_addobject (gdb_module, "Membuf", (PyObject *)
    905  1.1  christos 				 &membuf_object_type);
    906  1.1  christos }
    907  1.1  christos 
    908  1.1  christos static PyGetSetDef inferior_object_getset[] =
    909  1.1  christos {
    910  1.1  christos   { "num", infpy_get_num, NULL, "ID of inferior, as assigned by GDB.", NULL },
    911  1.1  christos   { "pid", infpy_get_pid, NULL, "PID of inferior, as assigned by the OS.",
    912  1.1  christos     NULL },
    913  1.1  christos   { "was_attached", infpy_get_was_attached, NULL,
    914  1.1  christos     "True if the inferior was created using 'attach'.", NULL },
    915  1.1  christos   { NULL }
    916  1.1  christos };
    917  1.1  christos 
    918  1.1  christos static PyMethodDef inferior_object_methods[] =
    919  1.1  christos {
    920  1.1  christos   { "is_valid", infpy_is_valid, METH_NOARGS,
    921  1.1  christos     "is_valid () -> Boolean.\n\
    922  1.1  christos Return true if this inferior is valid, false if not." },
    923  1.1  christos   { "threads", infpy_threads, METH_NOARGS,
    924  1.1  christos     "Return all the threads of this inferior." },
    925  1.1  christos   { "read_memory", (PyCFunction) infpy_read_memory,
    926  1.1  christos     METH_VARARGS | METH_KEYWORDS,
    927  1.1  christos     "read_memory (address, length) -> buffer\n\
    928  1.1  christos Return a buffer object for reading from the inferior's memory." },
    929  1.1  christos   { "write_memory", (PyCFunction) infpy_write_memory,
    930  1.1  christos     METH_VARARGS | METH_KEYWORDS,
    931  1.1  christos     "write_memory (address, buffer [, length])\n\
    932  1.1  christos Write the given buffer object to the inferior's memory." },
    933  1.1  christos   { "search_memory", (PyCFunction) infpy_search_memory,
    934  1.1  christos     METH_VARARGS | METH_KEYWORDS,
    935  1.1  christos     "search_memory (address, length, pattern) -> long\n\
    936  1.1  christos Return a long with the address of a match, or None." },
    937  1.1  christos   { NULL }
    938  1.1  christos };
    939  1.1  christos 
    940  1.5  christos PyTypeObject inferior_object_type =
    941  1.1  christos {
    942  1.1  christos   PyVarObject_HEAD_INIT (NULL, 0)
    943  1.1  christos   "gdb.Inferior",		  /* tp_name */
    944  1.1  christos   sizeof (inferior_object),	  /* tp_basicsize */
    945  1.1  christos   0,				  /* tp_itemsize */
    946  1.1  christos   infpy_dealloc,		  /* tp_dealloc */
    947  1.1  christos   0,				  /* tp_print */
    948  1.1  christos   0,				  /* tp_getattr */
    949  1.1  christos   0,				  /* tp_setattr */
    950  1.1  christos   0,				  /* tp_compare */
    951  1.1  christos   0,				  /* tp_repr */
    952  1.1  christos   0,				  /* tp_as_number */
    953  1.1  christos   0,				  /* tp_as_sequence */
    954  1.1  christos   0,				  /* tp_as_mapping */
    955  1.1  christos   0,				  /* tp_hash  */
    956  1.1  christos   0,				  /* tp_call */
    957  1.1  christos   0,				  /* tp_str */
    958  1.1  christos   0,				  /* tp_getattro */
    959  1.1  christos   0,				  /* tp_setattro */
    960  1.1  christos   0,				  /* tp_as_buffer */
    961  1.1  christos   Py_TPFLAGS_DEFAULT | Py_TPFLAGS_HAVE_ITER,  /* tp_flags */
    962  1.1  christos   "GDB inferior object",	  /* tp_doc */
    963  1.1  christos   0,				  /* tp_traverse */
    964  1.1  christos   0,				  /* tp_clear */
    965  1.1  christos   0,				  /* tp_richcompare */
    966  1.1  christos   0,				  /* tp_weaklistoffset */
    967  1.1  christos   0,				  /* tp_iter */
    968  1.1  christos   0,				  /* tp_iternext */
    969  1.1  christos   inferior_object_methods,	  /* tp_methods */
    970  1.1  christos   0,				  /* tp_members */
    971  1.1  christos   inferior_object_getset,	  /* tp_getset */
    972  1.1  christos   0,				  /* tp_base */
    973  1.1  christos   0,				  /* tp_dict */
    974  1.1  christos   0,				  /* tp_descr_get */
    975  1.1  christos   0,				  /* tp_descr_set */
    976  1.1  christos   0,				  /* tp_dictoffset */
    977  1.1  christos   0,				  /* tp_init */
    978  1.1  christos   0				  /* tp_alloc */
    979  1.1  christos };
    980  1.1  christos 
    981  1.1  christos #ifdef IS_PY3K
    982  1.1  christos 
    983  1.1  christos static PyBufferProcs buffer_procs =
    984  1.1  christos {
    985  1.1  christos   get_buffer
    986  1.1  christos };
    987  1.1  christos 
    988  1.1  christos #else
    989  1.1  christos 
    990  1.1  christos /* Python doesn't provide a decent way to get compatibility here.  */
    991  1.1  christos #if HAVE_LIBPYTHON2_4
    992  1.1  christos #define CHARBUFFERPROC_NAME getcharbufferproc
    993  1.1  christos #else
    994  1.1  christos #define CHARBUFFERPROC_NAME charbufferproc
    995  1.1  christos #endif
    996  1.1  christos 
    997  1.1  christos static PyBufferProcs buffer_procs = {
    998  1.1  christos   get_read_buffer,
    999  1.1  christos   get_write_buffer,
   1000  1.1  christos   get_seg_count,
   1001  1.1  christos   /* The cast here works around a difference between Python 2.4 and
   1002  1.1  christos      Python 2.5.  */
   1003  1.1  christos   (CHARBUFFERPROC_NAME) get_char_buffer
   1004  1.1  christos };
   1005  1.1  christos #endif	/* IS_PY3K */
   1006  1.1  christos 
   1007  1.5  christos PyTypeObject membuf_object_type = {
   1008  1.1  christos   PyVarObject_HEAD_INIT (NULL, 0)
   1009  1.1  christos   "gdb.Membuf",			  /*tp_name*/
   1010  1.1  christos   sizeof (membuf_object),	  /*tp_basicsize*/
   1011  1.1  christos   0,				  /*tp_itemsize*/
   1012  1.1  christos   mbpy_dealloc,			  /*tp_dealloc*/
   1013  1.1  christos   0,				  /*tp_print*/
   1014  1.1  christos   0,				  /*tp_getattr*/
   1015  1.1  christos   0,				  /*tp_setattr*/
   1016  1.1  christos   0,				  /*tp_compare*/
   1017  1.1  christos   0,				  /*tp_repr*/
   1018  1.1  christos   0,				  /*tp_as_number*/
   1019  1.1  christos   0,				  /*tp_as_sequence*/
   1020  1.1  christos   0,				  /*tp_as_mapping*/
   1021  1.1  christos   0,				  /*tp_hash */
   1022  1.1  christos   0,				  /*tp_call*/
   1023  1.1  christos   mbpy_str,			  /*tp_str*/
   1024  1.1  christos   0,				  /*tp_getattro*/
   1025  1.1  christos   0,				  /*tp_setattro*/
   1026  1.1  christos   &buffer_procs,		  /*tp_as_buffer*/
   1027  1.1  christos   Py_TPFLAGS_DEFAULT,		  /*tp_flags*/
   1028  1.1  christos   "GDB memory buffer object", 	  /*tp_doc*/
   1029  1.1  christos   0,				  /* tp_traverse */
   1030  1.1  christos   0,				  /* tp_clear */
   1031  1.1  christos   0,				  /* tp_richcompare */
   1032  1.1  christos   0,				  /* tp_weaklistoffset */
   1033  1.1  christos   0,				  /* tp_iter */
   1034  1.1  christos   0,				  /* tp_iternext */
   1035  1.1  christos   0,				  /* tp_methods */
   1036  1.1  christos   0,				  /* tp_members */
   1037  1.1  christos   0,				  /* tp_getset */
   1038  1.1  christos   0,				  /* tp_base */
   1039  1.1  christos   0,				  /* tp_dict */
   1040  1.1  christos   0,				  /* tp_descr_get */
   1041  1.1  christos   0,				  /* tp_descr_set */
   1042  1.1  christos   0,				  /* tp_dictoffset */
   1043  1.1  christos   0,				  /* tp_init */
   1044  1.1  christos   0,				  /* tp_alloc */
   1045  1.1  christos };
   1046