PEP 626:Guarantee stability of line table during release and define API for out-of-process tools. (#1555)
* Guarantee stability of line table during release and implement API for out-of-process tools.
This commit is contained in:
parent
c2c08f612c
commit
8dd402b7a9
59
pep-0626.rst
59
pep-0626.rst
|
@ -183,6 +183,57 @@ Access to the ``f_lineno`` attribute of frame objects through C API functions is
|
|||
|
||||
Accessing ``f_lineno`` directly through the underlying data structure is forbidden.
|
||||
|
||||
Out of process debuggers and profilers
|
||||
''''''''''''''''''''''''''''''''''''''
|
||||
|
||||
Out of process tools, such as py-spy [1]_, cannot use the C-API, and must parse the line number table themselves.
|
||||
Although the line number table format may change without warning,
|
||||
it will not change during a release unless absolutely necessary for a bug fix.
|
||||
|
||||
To reduce the work required to implement these tools, the following C struct and utility functions are provided.
|
||||
Note that these functions are not part of the C-API, so will be need to be linked into any code that needs to use them.
|
||||
|
||||
::
|
||||
|
||||
typedef struct addressrange {
|
||||
int ar_start;
|
||||
int ar_end;
|
||||
int ar_line;
|
||||
int opaque1;
|
||||
void *opaque2;
|
||||
} PyCodeAddressRange;
|
||||
|
||||
void PyLineTable_InitAddressRange(char *linetable, int firstlineno, PyCodeAddressRange *range);
|
||||
int PyLineTable_NextAddressRange(PyCodeAddressRange *range);
|
||||
int PyLineTable_PreviousAddressRange(PyCodeAddressRange *range);
|
||||
|
||||
``PyLineTable_InitAddressRange`` initializes the ``PyCodeAddressRange`` struct from the line number table and first line number.
|
||||
|
||||
``PyLineTable_NextAddressRange`` advances the range to the next entry, returning non-zero if valid.
|
||||
|
||||
``PyLineTable_PreviousAddressRange`` retreats the range to the previous entry, returning non-zero if valid.
|
||||
|
||||
For example, the following code prints out all the address ranges:
|
||||
|
||||
::
|
||||
|
||||
void print_address_ranges(char *linetable, int firstlineno)
|
||||
{
|
||||
PyCodeAddressRange range;
|
||||
PyLineTable_InitAddressRange(linetable, firstlineno, &range);
|
||||
while (PyLineTable_NextAddressRange(&range)) {
|
||||
printf("Bytecodes from %d (inclusive) to %d (exclusive) ",
|
||||
range.start, range.end);
|
||||
if (range.line < 0) {
|
||||
/* line < 0 means no line number */
|
||||
printf("have no line number\n");
|
||||
}
|
||||
else {
|
||||
printf("have line number %d\n", range.line);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
Performance Implications
|
||||
========================
|
||||
|
@ -194,7 +245,7 @@ Code with long sequences of ``pass`` statements will probably become a bit slowe
|
|||
Reference Implementation
|
||||
========================
|
||||
|
||||
Under development.
|
||||
https://github.com/markshannon/cpython/tree/new-linetable-format-version-2
|
||||
|
||||
Copyright
|
||||
=========
|
||||
|
@ -202,6 +253,12 @@ Copyright
|
|||
This document is placed in the public domain or under the
|
||||
CC0-1.0-Universal license, whichever is more permissive.
|
||||
|
||||
References
|
||||
==========
|
||||
|
||||
.. [1] py-spy: Sampling profiler for Python programs
|
||||
(https://github.com/benfred/py-spy)
|
||||
|
||||
|
||||
|
||||
..
|
||||
|
|
Loading…
Reference in New Issue