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