changeset: 101082:e4561aad29e6 branch: 2.7 parent: 101077:ac236f1e8fd4 user: Victor Stinner date: Wed Apr 20 18:23:13 2016 +0200 files: Misc/ACKS Misc/NEWS Tools/gdb/libpython.py description: Fix python-gdb.py: get C types on demand Issue #26799: Fix python-gdb.py: don't get C types once when the Python code is loaded, but get C types on demand. The C types can change if python-gdb.py is loaded before the Python executable. Patch written by Thomas Ilsche. diff -r ac236f1e8fd4 -r e4561aad29e6 Misc/ACKS --- a/Misc/ACKS Tue Apr 19 04:03:41 2016 +0000 +++ b/Misc/ACKS Wed Apr 20 18:23:13 2016 +0200 @@ -618,6 +618,7 @@ Mihai Ibanescu Ali Ikinci Aaron Iles +Thomas Ilsche Lars Immisch Bobby Impollonia Meador Inge diff -r ac236f1e8fd4 -r e4561aad29e6 Misc/NEWS --- a/Misc/NEWS Tue Apr 19 04:03:41 2016 +0000 +++ b/Misc/NEWS Wed Apr 20 18:23:13 2016 +0200 @@ -255,6 +255,14 @@ - Issue #25136: Support Apple Xcode 7's new textual SDK stub libraries. +Tools/Demos +----------- + +- Issue #26799: Fix python-gdb.py: don't get C types once when the Python code + is loaded, but get C types on demand. The C types can change if + python-gdb.py is loaded before the Python executable. Patch written by Thomas + Ilsche. + C API ----- diff -r ac236f1e8fd4 -r e4561aad29e6 Tools/gdb/libpython.py --- a/Tools/gdb/libpython.py Tue Apr 19 04:03:41 2016 +0000 +++ b/Tools/gdb/libpython.py Wed Apr 20 18:23:13 2016 +0200 @@ -55,11 +55,19 @@ long = int # Look up the gdb.Type for some standard types: -_type_char_ptr = gdb.lookup_type('char').pointer() # char* -_type_unsigned_char_ptr = gdb.lookup_type('unsigned char').pointer() # unsigned char* -_type_void_ptr = gdb.lookup_type('void').pointer() # void* +# Those need to be refreshed as types (pointer sizes) may change when +# gdb loads different executables + +def _type_char_ptr(): + return gdb.lookup_type('char').pointer() # char* + -SIZEOF_VOID_P = _type_void_ptr.sizeof +def _type_unsigned_char_ptr(): + return gdb.lookup_type('unsigned char').pointer() # unsigned char* + + +def _sizeof_void_p(): + return gdb.lookup_type('void').pointer().sizeof Py_TPFLAGS_HEAPTYPE = (1 << 9) @@ -439,8 +447,8 @@ return ( ( typeobj.field('tp_basicsize') + nitems * typeobj.field('tp_itemsize') + - (SIZEOF_VOID_P - 1) - ) & ~(SIZEOF_VOID_P - 1) + (_sizeof_void_p() - 1) + ) & ~(_sizeof_void_p() - 1) ).cast(_PyObject_VAR_SIZE._type_size_t) _PyObject_VAR_SIZE._type_size_t = None @@ -464,9 +472,9 @@ size = _PyObject_VAR_SIZE(typeobj, tsize) dictoffset += size assert dictoffset > 0 - assert dictoffset % SIZEOF_VOID_P == 0 + assert dictoffset % _sizeof_void_p() == 0 - dictptr = self._gdbval.cast(_type_char_ptr) + dictoffset + dictptr = self._gdbval.cast(_type_char_ptr()) + dictoffset PyObjectPtrPtr = PyObjectPtr.get_gdb_type().pointer() dictptr = dictptr.cast(PyObjectPtrPtr) return PyObjectPtr.from_pyobject_ptr(dictptr.dereference()) @@ -1014,7 +1022,7 @@ def __str__(self): field_ob_size = self.field('ob_size') field_ob_sval = self.field('ob_sval') - char_ptr = field_ob_sval.address.cast(_type_unsigned_char_ptr) + char_ptr = field_ob_sval.address.cast(_type_unsigned_char_ptr()) # When gdb is linked with a Python 3 interpreter, this is really # a latin-1 mojibake decoding of the original string... return ''.join([chr(char_ptr[i]) for i in safe_range(field_ob_size)])