[Cython] Help with cygdb bug

Stefan Behnel stefan_ml at behnel.de
Thu Apr 23 08:30:49 EDT 2020


Hi Volker!

Volker Weißmann schrieb am 22.04.20 um 20:44:
> cy exec print(localvar)
> 
> currently does not work. And I need your help to fix it.

Do you mean "cy exec print(x)" or "cy print x" here? (The latter is what
you used in your example at the end.)


> If I'm not mistaken, the function "_fill_locals_dict" in libcython.py is
> supposed to find and set all local variables.
> 
> The "for name, cyvar in iterator:" correctly iterates over all local
> variables, but cyvar.type is not PythonObject but CObject.
> 
> The cython line "localvar= 49" gets translated to the C-line
> "__pyx_v_localvar = 49;". Notice how the type of__pyx_v_localvar is long
> and not a static PyObject*  . If an equivalent "static PyObject*" would
> exist in the C-code, I would know how to make 'cy exec print(localvar)'
> work (the reason why global variables work, is because they are of type
> static PyObject*).

I think I could live with the Python code "print(localvar)" not working, as
long as I have something like "p localvar" and "pyo localvar". I guess the
issue here is the name mangling, which should happen automatically.

Can't we map "cy print x" to "p __pyx_v_x" for C types and "pyo __pyx_v_x"
for Python object types? (And, isn't that how it works right now?)


> I see two ways to make `cy exec print(localvar)` work:
> 
> 1. Let cygdb generate C-code to convert a long (or any other type) to an
> equivalent static PyObject* (For long's it would be
> __Pyx_PyInt_From_long). Then let cygdb execute this code by running
> gdb.parse_and_eval(code). Then read the resulting variable with
> something like
> 
> code = '''
>                     (PyObject *) PyDict_SetItem(
>                         (PyObject *) %d,
>                         (PyObject *) %d,
>                         (PyObject *) %s)
>                 ''' % (local_dict_pointer, pystringp, cname)
> 
> gdb.parse_and_eval(code)

I'd rather not go take that route. If it's a C value, gdb should be able to
print it. We should better not go through Python here.


> 2. Compile the argument of cy exec (in this case "print(localvar)") to
> C-code (while getting the local variables right) and run it using
> gdb.parse_and_eval(code).
> 
> 
> Ideally, cy exec var=123 should work like cy set var=123.

That seems a cool feature – but also a lot of implementation work. My gut
feeling is that there may be tons of special cases where code needs to be
adapted somehow before or after the code generation in order to make it do
what users would expect it to do.

I'd rather like to avoid complexity where we can.

Stefan


More information about the cython-devel mailing list