help-gnu-emacs
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

Re: Executing Emacs commands when a gdb breakpoint is hit


From: Skip Montanaro
Subject: Re: Executing Emacs commands when a gdb breakpoint is hit
Date: Wed, 22 Jan 2020 15:07:57 -0600

> I don't think I understand what you are trying to do and what are the
> difficulties, sorry.

My apologies. As is so often true with things we work on, it's easy to
forget that others aren't as steeped in our problems. It's easy to
assume more of one's audience. Here's some more detail.

I'm working on the Python bytecode compiler. It's written in C. As I
work my way through the process, I want to know where the compiler is
currently working. The compiler maintains a number of C structs
throughout the process. At the top level is the compiler struct. Here
I've only displayed the two fields of interest to me. The c_filename
field names the file being compiled. The compiler_unit * field refers
to a subsidiary struct which contains (among other bits) the current
line and column offset of the current statement being compiled.

struct compiler {
    PyObject *c_filename;
    ...
    struct compiler_unit *u; /* compiler state for current block */
    ...
};

struct compiler_unit {
    ...
    int u_lineno;          /* the lineno for the current stmt */
    int u_col_offset;      /* the offset of the current stmt */
    ...
};

So, I run Python under control of gdb and set a breakpoint in a
specific function, compiler_set_lineno. When this breakpoint is
reached, I want to query gdb for the current values of c->c_filename
and c->u->u_lineno. The first argument to that function is struct
compiler *c. Eventually, I will likely be interested in more fields of
either of these structs, but for the purposes of interacting with gdb,
this is sufficient.

I wrote an ELisp function which is an element of the
gdb-stopped-functions list. It gets called at the appropriate place
when the breakpoint is encountered. I get a useful reason argument for
the stoppage and, in particular, can tell whether or not the stoppage
occurred in compiler_set_lineno. When this is the case (I might have
breakpoints set elsewhere, so would want to bail out if that was the
case), I want to evaluate the current Python filename, line number and
column. That allows me to update display of the Python file within
Emacs and so get a bit of visual context for where the compiler is
working. (It works from an abstract syntax tree which is pretty low
level. Viewing the compilation context in the source file is quite
useful.)

The problem I encounter is that the underlying gdb process doesn't
seem to be ready to receive input when my stop function is executed.
It appears to have been stopped, but the (gdb) prompt isn't visible in
the *gud-python* buffer. I want to print the desired expression with
(comint-send-input), then read the result. Perhaps I should just set a
gdb-level command to print the desired expressions instead. My ELisp
code would only then need to read the values from *gud-python*. The
advantage of doing everything from within my ELisp stop function is
that everything relevant to this display lives in one place. I don't
have to synchronize my ELisp with user-level gdb commands.

Perhaps there is a comint function which will update the *gud-python*
buffer so the (gdb) prompt is visible and the underlying gdb process
is truly ready for (comint-send-input)?

Skip



reply via email to

[Prev in Thread] Current Thread [Next in Thread]