mirror of
https://sourceware.org/git/binutils-gdb.git
synced 2024-12-21 04:42:53 +08:00
230d2906b9
This renames the gdb exception types. The old types were only needed due to the macros in common-exception.h that are now gone. The intermediate layer of gdb_exception_RETURN_MASK_ALL did not seem needed, so this patch removes it entirely. gdb/ChangeLog 2019-04-08 Tom Tromey <tom@tromey.com> * common/common-exceptions.h (gdb_exception_RETURN_MASK_ALL): Remove. (gdb_exception_error): Rename from gdb_exception_RETURN_MASK_ERROR. (gdb_exception_quit): Rename from gdb_exception_RETURN_MASK_QUIT. (gdb_quit_bad_alloc): Update. * aarch64-tdep.c: Update. * ada-lang.c: Update. * ada-typeprint.c: Update. * ada-valprint.c: Update. * amd64-tdep.c: Update. * arch-utils.c: Update. * break-catch-throw.c: Update. * breakpoint.c: Update. * btrace.c: Update. * c-varobj.c: Update. * cli/cli-cmds.c: Update. * cli/cli-interp.c: Update. * cli/cli-script.c: Update. * common/common-exceptions.c: Update. * common/new-op.c: Update. * common/selftest.c: Update. * compile/compile-c-symbols.c: Update. * compile/compile-cplus-symbols.c: Update. * compile/compile-object-load.c: Update. * compile/compile-object-run.c: Update. * completer.c: Update. * corelow.c: Update. * cp-abi.c: Update. * cp-support.c: Update. * cp-valprint.c: Update. * darwin-nat.c: Update. * disasm-selftests.c: Update. * dtrace-probe.c: Update. * dwarf-index-cache.c: Update. * dwarf-index-write.c: Update. * dwarf2-frame-tailcall.c: Update. * dwarf2-frame.c: Update. * dwarf2loc.c: Update. * dwarf2read.c: Update. * eval.c: Update. * event-loop.c: Update. * event-top.c: Update. * exec.c: Update. * f-valprint.c: Update. * fbsd-tdep.c: Update. * frame-unwind.c: Update. * frame.c: Update. * gdbtypes.c: Update. * gnu-v3-abi.c: Update. * guile/guile-internal.h: Update. * guile/scm-block.c: Update. * guile/scm-breakpoint.c: Update. * guile/scm-cmd.c: Update. * guile/scm-disasm.c: Update. * guile/scm-frame.c: Update. * guile/scm-lazy-string.c: Update. * guile/scm-math.c: Update. * guile/scm-param.c: Update. * guile/scm-ports.c: Update. * guile/scm-pretty-print.c: Update. * guile/scm-symbol.c: Update. * guile/scm-symtab.c: Update. * guile/scm-type.c: Update. * guile/scm-value.c: Update. * i386-linux-tdep.c: Update. * i386-tdep.c: Update. * inf-loop.c: Update. * infcall.c: Update. * infcmd.c: Update. * infrun.c: Update. * jit.c: Update. * language.c: Update. * linespec.c: Update. * linux-fork.c: Update. * linux-nat.c: Update. * linux-tdep.c: Update. * linux-thread-db.c: Update. * main.c: Update. * mi/mi-cmd-break.c: Update. * mi/mi-cmd-stack.c: Update. * mi/mi-interp.c: Update. * mi/mi-main.c: Update. * objc-lang.c: Update. * p-valprint.c: Update. * parse.c: Update. * ppc-linux-tdep.c: Update. * printcmd.c: Update. * python/py-arch.c: Update. * python/py-breakpoint.c: Update. * python/py-cmd.c: Update. * python/py-finishbreakpoint.c: Update. * python/py-frame.c: Update. * python/py-framefilter.c: Update. * python/py-gdb-readline.c: Update. * python/py-inferior.c: Update. * python/py-infthread.c: Update. * python/py-lazy-string.c: Update. * python/py-linetable.c: Update. * python/py-objfile.c: Update. * python/py-param.c: Update. * python/py-prettyprint.c: Update. * python/py-progspace.c: Update. * python/py-record-btrace.c: Update. * python/py-record.c: Update. * python/py-symbol.c: Update. * python/py-type.c: Update. * python/py-unwind.c: Update. * python/py-utils.c: Update. * python/py-value.c: Update. * python/python.c: Update. * record-btrace.c: Update. * record-full.c: Update. * remote-fileio.c: Update. * remote.c: Update. * riscv-tdep.c: Update. * rs6000-aix-tdep.c: Update. * rs6000-tdep.c: Update. * rust-exp.y: Update. * rust-lang.c: Update. * s390-tdep.c: Update. * selftest-arch.c: Update. * solib-dsbt.c: Update. * solib-frv.c: Update. * solib-spu.c: Update. * solib-svr4.c: Update. * solib.c: Update. * sparc64-linux-tdep.c: Update. * stack.c: Update. * symfile-mem.c: Update. * symmisc.c: Update. * target.c: Update. * thread.c: Update. * top.c: Update. * tracefile-tfile.c: Update. * tui/tui.c: Update. * typeprint.c: Update. * unittests/cli-utils-selftests.c: Update. * unittests/parse-connection-spec-selftests.c: Update. * valops.c: Update. * valprint.c: Update. * value.c: Update. * varobj.c: Update. * windows-nat.c: Update. * x86-linux-nat.c: Update. * xml-support.c: Update. gdb/gdbserver/ChangeLog 2019-04-08 Tom Tromey <tom@tromey.com> * gdbreplay.c: Update. * linux-low.c: Update. * server.c: Update.
294 lines
9.4 KiB
C
294 lines
9.4 KiB
C
/* Python interface to architecture
|
|
|
|
Copyright (C) 2013-2019 Free Software Foundation, Inc.
|
|
|
|
This file is part of GDB.
|
|
|
|
This program is free software; you can redistribute it and/or modify
|
|
it under the terms of the GNU General Public License as published by
|
|
the Free Software Foundation; either version 3 of the License, or
|
|
(at your option) any later version.
|
|
|
|
This program is distributed in the hope that it will be useful,
|
|
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
GNU General Public License for more details.
|
|
|
|
You should have received a copy of the GNU General Public License
|
|
along with this program. If not, see <http://www.gnu.org/licenses/>. */
|
|
|
|
#include "defs.h"
|
|
#include "gdbarch.h"
|
|
#include "arch-utils.h"
|
|
#include "disasm.h"
|
|
#include "python-internal.h"
|
|
|
|
typedef struct arch_object_type_object {
|
|
PyObject_HEAD
|
|
struct gdbarch *gdbarch;
|
|
} arch_object;
|
|
|
|
static struct gdbarch_data *arch_object_data = NULL;
|
|
|
|
/* Require a valid Architecture. */
|
|
#define ARCHPY_REQUIRE_VALID(arch_obj, arch) \
|
|
do { \
|
|
arch = arch_object_to_gdbarch (arch_obj); \
|
|
if (arch == NULL) \
|
|
{ \
|
|
PyErr_SetString (PyExc_RuntimeError, \
|
|
_("Architecture is invalid.")); \
|
|
return NULL; \
|
|
} \
|
|
} while (0)
|
|
|
|
extern PyTypeObject arch_object_type
|
|
CPYCHECKER_TYPE_OBJECT_FOR_TYPEDEF ("arch_object");
|
|
|
|
/* Associates an arch_object with GDBARCH as gdbarch_data via the gdbarch
|
|
post init registration mechanism (gdbarch_data_register_post_init). */
|
|
|
|
static void *
|
|
arch_object_data_init (struct gdbarch *gdbarch)
|
|
{
|
|
arch_object *arch_obj = PyObject_New (arch_object, &arch_object_type);
|
|
|
|
if (arch_obj == NULL)
|
|
return NULL;
|
|
|
|
arch_obj->gdbarch = gdbarch;
|
|
|
|
return (void *) arch_obj;
|
|
}
|
|
|
|
/* Returns the struct gdbarch value corresponding to the given Python
|
|
architecture object OBJ. */
|
|
|
|
struct gdbarch *
|
|
arch_object_to_gdbarch (PyObject *obj)
|
|
{
|
|
arch_object *py_arch = (arch_object *) obj;
|
|
|
|
return py_arch->gdbarch;
|
|
}
|
|
|
|
/* Returns the Python architecture object corresponding to GDBARCH.
|
|
Returns a new reference to the arch_object associated as data with
|
|
GDBARCH. */
|
|
|
|
PyObject *
|
|
gdbarch_to_arch_object (struct gdbarch *gdbarch)
|
|
{
|
|
PyObject *new_ref = (PyObject *) gdbarch_data (gdbarch, arch_object_data);
|
|
|
|
/* new_ref could be NULL if registration of arch_object with GDBARCH failed
|
|
in arch_object_data_init. */
|
|
Py_XINCREF (new_ref);
|
|
|
|
return new_ref;
|
|
}
|
|
|
|
/* Implementation of gdb.Architecture.name (self) -> String.
|
|
Returns the name of the architecture as a string value. */
|
|
|
|
static PyObject *
|
|
archpy_name (PyObject *self, PyObject *args)
|
|
{
|
|
struct gdbarch *gdbarch = NULL;
|
|
const char *name;
|
|
|
|
ARCHPY_REQUIRE_VALID (self, gdbarch);
|
|
|
|
name = (gdbarch_bfd_arch_info (gdbarch))->printable_name;
|
|
return PyString_FromString (name);
|
|
}
|
|
|
|
/* Implementation of
|
|
gdb.Architecture.disassemble (self, start_pc [, end_pc [,count]]) -> List.
|
|
Returns a list of instructions in a memory address range. Each instruction
|
|
in the list is a Python dict object.
|
|
*/
|
|
|
|
static PyObject *
|
|
archpy_disassemble (PyObject *self, PyObject *args, PyObject *kw)
|
|
{
|
|
static const char *keywords[] = { "start_pc", "end_pc", "count", NULL };
|
|
CORE_ADDR start, end = 0;
|
|
CORE_ADDR pc;
|
|
gdb_py_ulongest start_temp;
|
|
long count = 0, i;
|
|
PyObject *end_obj = NULL, *count_obj = NULL;
|
|
struct gdbarch *gdbarch = NULL;
|
|
|
|
ARCHPY_REQUIRE_VALID (self, gdbarch);
|
|
|
|
if (!gdb_PyArg_ParseTupleAndKeywords (args, kw, GDB_PY_LLU_ARG "|OO",
|
|
keywords, &start_temp, &end_obj,
|
|
&count_obj))
|
|
return NULL;
|
|
|
|
start = start_temp;
|
|
if (end_obj)
|
|
{
|
|
/* Make a long logic check first. In Python 3.x, internally,
|
|
all integers are represented as longs. In Python 2.x, there
|
|
is still a differentiation internally between a PyInt and a
|
|
PyLong. Explicitly do this long check conversion first. In
|
|
GDB, for Python 3.x, we #ifdef PyInt = PyLong. This check has
|
|
to be done first to ensure we do not lose information in the
|
|
conversion process. */
|
|
if (PyLong_Check (end_obj))
|
|
end = PyLong_AsUnsignedLongLong (end_obj);
|
|
#if PY_MAJOR_VERSION == 2
|
|
else if (PyInt_Check (end_obj))
|
|
/* If the end_pc value is specified without a trailing 'L', end_obj will
|
|
be an integer and not a long integer. */
|
|
end = PyInt_AsLong (end_obj);
|
|
#endif
|
|
else
|
|
{
|
|
PyErr_SetString (PyExc_TypeError,
|
|
_("Argument 'end_pc' should be a (long) integer."));
|
|
|
|
return NULL;
|
|
}
|
|
|
|
if (end < start)
|
|
{
|
|
PyErr_SetString (PyExc_ValueError,
|
|
_("Argument 'end_pc' should be greater than or "
|
|
"equal to the argument 'start_pc'."));
|
|
|
|
return NULL;
|
|
}
|
|
}
|
|
if (count_obj)
|
|
{
|
|
count = PyInt_AsLong (count_obj);
|
|
if (PyErr_Occurred () || count < 0)
|
|
{
|
|
PyErr_SetString (PyExc_TypeError,
|
|
_("Argument 'count' should be an non-negative "
|
|
"integer."));
|
|
|
|
return NULL;
|
|
}
|
|
}
|
|
|
|
gdbpy_ref<> result_list (PyList_New (0));
|
|
if (result_list == NULL)
|
|
return NULL;
|
|
|
|
for (pc = start, i = 0;
|
|
/* All args are specified. */
|
|
(end_obj && count_obj && pc <= end && i < count)
|
|
/* end_pc is specified, but no count. */
|
|
|| (end_obj && count_obj == NULL && pc <= end)
|
|
/* end_pc is not specified, but a count is. */
|
|
|| (end_obj == NULL && count_obj && i < count)
|
|
/* Both end_pc and count are not specified. */
|
|
|| (end_obj == NULL && count_obj == NULL && pc == start);)
|
|
{
|
|
int insn_len = 0;
|
|
gdbpy_ref<> insn_dict (PyDict_New ());
|
|
|
|
if (insn_dict == NULL)
|
|
return NULL;
|
|
if (PyList_Append (result_list.get (), insn_dict.get ()))
|
|
return NULL; /* PyList_Append Sets the exception. */
|
|
|
|
string_file stb;
|
|
|
|
try
|
|
{
|
|
insn_len = gdb_print_insn (gdbarch, pc, &stb, NULL);
|
|
}
|
|
catch (const gdb_exception &except)
|
|
{
|
|
gdbpy_convert_exception (except);
|
|
return NULL;
|
|
}
|
|
|
|
if (PyDict_SetItemString (insn_dict.get (), "addr",
|
|
gdb_py_long_from_ulongest (pc))
|
|
|| PyDict_SetItemString (insn_dict.get (), "asm",
|
|
PyString_FromString (!stb.empty ()
|
|
? stb.c_str ()
|
|
: "<unknown>"))
|
|
|| PyDict_SetItemString (insn_dict.get (), "length",
|
|
PyInt_FromLong (insn_len)))
|
|
return NULL;
|
|
|
|
pc += insn_len;
|
|
i++;
|
|
}
|
|
|
|
return result_list.release ();
|
|
}
|
|
|
|
/* Initializes the Architecture class in the gdb module. */
|
|
|
|
int
|
|
gdbpy_initialize_arch (void)
|
|
{
|
|
arch_object_data = gdbarch_data_register_post_init (arch_object_data_init);
|
|
arch_object_type.tp_new = PyType_GenericNew;
|
|
if (PyType_Ready (&arch_object_type) < 0)
|
|
return -1;
|
|
|
|
return gdb_pymodule_addobject (gdb_module, "Architecture",
|
|
(PyObject *) &arch_object_type);
|
|
}
|
|
|
|
static PyMethodDef arch_object_methods [] = {
|
|
{ "name", archpy_name, METH_NOARGS,
|
|
"name () -> String.\n\
|
|
Return the name of the architecture as a string value." },
|
|
{ "disassemble", (PyCFunction) archpy_disassemble,
|
|
METH_VARARGS | METH_KEYWORDS,
|
|
"disassemble (start_pc [, end_pc [, count]]) -> List.\n\
|
|
Return a list of at most COUNT disassembled instructions from START_PC to\n\
|
|
END_PC." },
|
|
{NULL} /* Sentinel */
|
|
};
|
|
|
|
PyTypeObject arch_object_type = {
|
|
PyVarObject_HEAD_INIT (NULL, 0)
|
|
"gdb.Architecture", /* tp_name */
|
|
sizeof (arch_object), /* tp_basicsize */
|
|
0, /* tp_itemsize */
|
|
0, /* tp_dealloc */
|
|
0, /* tp_print */
|
|
0, /* tp_getattr */
|
|
0, /* tp_setattr */
|
|
0, /* tp_compare */
|
|
0, /* tp_repr */
|
|
0, /* tp_as_number */
|
|
0, /* tp_as_sequence */
|
|
0, /* tp_as_mapping */
|
|
0, /* tp_hash */
|
|
0, /* tp_call */
|
|
0, /* tp_str */
|
|
0, /* tp_getattro */
|
|
0, /* tp_setattro */
|
|
0, /* tp_as_buffer */
|
|
Py_TPFLAGS_DEFAULT, /* tp_flags */
|
|
"GDB architecture object", /* tp_doc */
|
|
0, /* tp_traverse */
|
|
0, /* tp_clear */
|
|
0, /* tp_richcompare */
|
|
0, /* tp_weaklistoffset */
|
|
0, /* tp_iter */
|
|
0, /* tp_iternext */
|
|
arch_object_methods, /* tp_methods */
|
|
0, /* tp_members */
|
|
0, /* tp_getset */
|
|
0, /* tp_base */
|
|
0, /* tp_dict */
|
|
0, /* tp_descr_get */
|
|
0, /* tp_descr_set */
|
|
0, /* tp_dictoffset */
|
|
0, /* tp_init */
|
|
0, /* tp_alloc */
|
|
};
|