pystack 1.3.0__tar.gz → 1.4.1__tar.gz

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (85) hide show
  1. {pystack-1.3.0 → pystack-1.4.1}/.bumpversion.cfg +1 -1
  2. {pystack-1.3.0 → pystack-1.4.1}/Makefile +5 -0
  3. {pystack-1.3.0 → pystack-1.4.1}/NEWS.rst +29 -0
  4. {pystack-1.3.0 → pystack-1.4.1}/PKG-INFO +2 -1
  5. {pystack-1.3.0 → pystack-1.4.1}/pyproject.toml +6 -0
  6. {pystack-1.3.0 → pystack-1.4.1}/setup.py +1 -0
  7. {pystack-1.3.0 → pystack-1.4.1}/src/pystack/__main__.py +29 -0
  8. {pystack-1.3.0 → pystack-1.4.1}/src/pystack/_pystack/corefile.cpp +1 -0
  9. {pystack-1.3.0 → pystack-1.4.1}/src/pystack/_pystack/cpython/code.h +35 -7
  10. {pystack-1.3.0 → pystack-1.4.1}/src/pystack/_pystack/cpython/dict.h +19 -1
  11. {pystack-1.3.0 → pystack-1.4.1}/src/pystack/_pystack/cpython/frame.h +2 -10
  12. {pystack-1.3.0 → pystack-1.4.1}/src/pystack/_pystack/cpython/gc.h +0 -5
  13. {pystack-1.3.0 → pystack-1.4.1}/src/pystack/_pystack/cpython/interpreter.h +90 -8
  14. {pystack-1.3.0 → pystack-1.4.1}/src/pystack/_pystack/cpython/object.h +0 -6
  15. {pystack-1.3.0 → pystack-1.4.1}/src/pystack/_pystack/cpython/runtime.h +179 -2
  16. {pystack-1.3.0 → pystack-1.4.1}/src/pystack/_pystack/cpython/string.h +17 -24
  17. {pystack-1.3.0 → pystack-1.4.1}/src/pystack/_pystack/cpython/thread.h +60 -11
  18. {pystack-1.3.0 → pystack-1.4.1}/src/pystack/_pystack/mem.cpp +2 -2
  19. pystack-1.4.1/src/pystack/_pystack/process.cpp +1379 -0
  20. {pystack-1.3.0 → pystack-1.4.1}/src/pystack/_pystack/process.h +19 -15
  21. {pystack-1.3.0 → pystack-1.4.1}/src/pystack/_pystack/process.pxd +3 -1
  22. {pystack-1.3.0 → pystack-1.4.1}/src/pystack/_pystack/pycode.cpp +19 -10
  23. {pystack-1.3.0 → pystack-1.4.1}/src/pystack/_pystack/pycode.h +1 -2
  24. {pystack-1.3.0 → pystack-1.4.1}/src/pystack/_pystack/pyframe.cpp +46 -39
  25. {pystack-1.3.0 → pystack-1.4.1}/src/pystack/_pystack/pyframe.h +10 -9
  26. {pystack-1.3.0 → pystack-1.4.1}/src/pystack/_pystack/pyframe.pxd +1 -0
  27. {pystack-1.3.0 → pystack-1.4.1}/src/pystack/_pystack/pythread.cpp +41 -56
  28. {pystack-1.3.0 → pystack-1.4.1}/src/pystack/_pystack/pythread.h +6 -5
  29. {pystack-1.3.0 → pystack-1.4.1}/src/pystack/_pystack/pytypes.cpp +97 -71
  30. {pystack-1.3.0 → pystack-1.4.1}/src/pystack/_pystack/pytypes.h +6 -4
  31. pystack-1.4.1/src/pystack/_pystack/structure.h +91 -0
  32. {pystack-1.3.0 → pystack-1.4.1}/src/pystack/_pystack/unwinder.cpp +1 -0
  33. pystack-1.4.1/src/pystack/_pystack/version.cpp +761 -0
  34. pystack-1.4.1/src/pystack/_pystack/version.h +323 -0
  35. {pystack-1.3.0 → pystack-1.4.1}/src/pystack/_pystack.pyi +3 -1
  36. {pystack-1.3.0 → pystack-1.4.1}/src/pystack/_pystack.pyx +21 -4
  37. pystack-1.4.1/src/pystack/_version.py +1 -0
  38. {pystack-1.3.0 → pystack-1.4.1}/src/pystack/process.py +47 -1
  39. {pystack-1.3.0 → pystack-1.4.1}/src/pystack/traceback_formatter.py +4 -4
  40. {pystack-1.3.0 → pystack-1.4.1}/src/pystack/types.py +9 -0
  41. {pystack-1.3.0 → pystack-1.4.1}/src/pystack.egg-info/PKG-INFO +2 -1
  42. {pystack-1.3.0 → pystack-1.4.1}/src/pystack.egg-info/SOURCES.txt +1 -0
  43. pystack-1.3.0/src/pystack/_pystack/process.cpp +0 -667
  44. pystack-1.3.0/src/pystack/_pystack/version.cpp +0 -401
  45. pystack-1.3.0/src/pystack/_pystack/version.h +0 -141
  46. pystack-1.3.0/src/pystack/_version.py +0 -1
  47. {pystack-1.3.0 → pystack-1.4.1}/.pre-commit-config.yaml +0 -0
  48. {pystack-1.3.0 → pystack-1.4.1}/LICENSE +0 -0
  49. {pystack-1.3.0 → pystack-1.4.1}/MANIFEST.in +0 -0
  50. {pystack-1.3.0 → pystack-1.4.1}/README.md +0 -0
  51. {pystack-1.3.0 → pystack-1.4.1}/build_scripts/elfutils_contiguous_segments.diff +0 -0
  52. {pystack-1.3.0 → pystack-1.4.1}/setup.cfg +0 -0
  53. {pystack-1.3.0 → pystack-1.4.1}/src/pystack/__init__.py +0 -0
  54. {pystack-1.3.0 → pystack-1.4.1}/src/pystack/_pystack/CMakeLists.txt +0 -0
  55. {pystack-1.3.0 → pystack-1.4.1}/src/pystack/_pystack/__init__.pxd +0 -0
  56. {pystack-1.3.0 → pystack-1.4.1}/src/pystack/_pystack/compat.h +0 -0
  57. {pystack-1.3.0 → pystack-1.4.1}/src/pystack/_pystack/corefile.h +0 -0
  58. {pystack-1.3.0 → pystack-1.4.1}/src/pystack/_pystack/corefile.pxd +0 -0
  59. {pystack-1.3.0 → pystack-1.4.1}/src/pystack/_pystack/cpython/float.h +0 -0
  60. {pystack-1.3.0 → pystack-1.4.1}/src/pystack/_pystack/cpython/int.h +0 -0
  61. {pystack-1.3.0 → pystack-1.4.1}/src/pystack/_pystack/cpython/list.h +0 -0
  62. {pystack-1.3.0 → pystack-1.4.1}/src/pystack/_pystack/cpython/pthread.h +0 -0
  63. {pystack-1.3.0 → pystack-1.4.1}/src/pystack/_pystack/cpython/tuple.h +0 -0
  64. {pystack-1.3.0 → pystack-1.4.1}/src/pystack/_pystack/elf_common.cpp +0 -0
  65. {pystack-1.3.0 → pystack-1.4.1}/src/pystack/_pystack/elf_common.h +0 -0
  66. {pystack-1.3.0 → pystack-1.4.1}/src/pystack/_pystack/elf_common.pxd +0 -0
  67. {pystack-1.3.0 → pystack-1.4.1}/src/pystack/_pystack/logging.cpp +0 -0
  68. {pystack-1.3.0 → pystack-1.4.1}/src/pystack/_pystack/logging.h +0 -0
  69. {pystack-1.3.0 → pystack-1.4.1}/src/pystack/_pystack/logging.pxd +0 -0
  70. {pystack-1.3.0 → pystack-1.4.1}/src/pystack/_pystack/mem.h +0 -0
  71. {pystack-1.3.0 → pystack-1.4.1}/src/pystack/_pystack/mem.pxd +0 -0
  72. {pystack-1.3.0 → pystack-1.4.1}/src/pystack/_pystack/native_frame.h +0 -0
  73. {pystack-1.3.0 → pystack-1.4.1}/src/pystack/_pystack/native_frame.pxd +0 -0
  74. {pystack-1.3.0 → pystack-1.4.1}/src/pystack/_pystack/pycode.pxd +0 -0
  75. {pystack-1.3.0 → pystack-1.4.1}/src/pystack/_pystack/pycompat.h +0 -0
  76. {pystack-1.3.0 → pystack-1.4.1}/src/pystack/_pystack/pythread.pxd +0 -0
  77. {pystack-1.3.0 → pystack-1.4.1}/src/pystack/_pystack/unwinder.h +0 -0
  78. {pystack-1.3.0 → pystack-1.4.1}/src/pystack/colors.py +0 -0
  79. {pystack-1.3.0 → pystack-1.4.1}/src/pystack/engine.py +0 -0
  80. {pystack-1.3.0 → pystack-1.4.1}/src/pystack/errors.py +0 -0
  81. {pystack-1.3.0 → pystack-1.4.1}/src/pystack/maps.py +0 -0
  82. {pystack-1.3.0 → pystack-1.4.1}/src/pystack/py.typed +0 -0
  83. {pystack-1.3.0 → pystack-1.4.1}/src/pystack.egg-info/dependency_links.txt +0 -0
  84. {pystack-1.3.0 → pystack-1.4.1}/src/pystack.egg-info/entry_points.txt +0 -0
  85. {pystack-1.3.0 → pystack-1.4.1}/src/pystack.egg-info/top_level.txt +0 -0
@@ -1,5 +1,5 @@
1
1
  [bumpversion]
2
- current_version = 1.3.0
2
+ current_version = 1.4.1
3
3
  commit = True
4
4
  message =
5
5
  Prepare for {new_version} release
@@ -93,6 +93,11 @@ docs: ## Generate documentation
93
93
  $(MAKE) -C docs clean
94
94
  $(MAKE) -C docs html
95
95
 
96
+ .PHONY: docs-live
97
+ docs-live: ## Serve documentation on localhost:8000, with live-reload
98
+ $(MAKE) -C docs clean
99
+ $(MAKE) -C docs livehtml
100
+
96
101
  .PHONY: gh-pages
97
102
  gh-pages: ## Publish documentation on GitHub Pages
98
103
  $(eval GIT_REMOTE := $(shell git remote get-url $(UPSTREAM_GIT_REMOTE)))
@@ -8,6 +8,35 @@ Changelog
8
8
 
9
9
  .. towncrier release notes start
10
10
 
11
+ pystack 1.4.1 (2024-10-04)
12
+ --------------------------
13
+
14
+ Features
15
+ ~~~~~~~~
16
+
17
+ - Improve our ability to debug Python 3.13 processes when the ``_Py_DebugOffsets`` cannot be located by accounting for a structure layout change in CPython 3.13.0rc3 (the reversion of the incremental cyclic garbage collector). (#213)
18
+
19
+
20
+ pystack 1.4.0 (2024-09-11)
21
+ --------------------------
22
+
23
+ Features
24
+ ~~~~~~~~
25
+
26
+ - Add support for Python 3.13 (#186)
27
+ - Add support for gzip compressed corefiles (#171)
28
+ - Add a new ``--version`` command line flag to show the version of pystack (#203)
29
+ - Support debugging free-threading (a.k.a. "nogil") Python 3.13 builds. Note that PyStack can't itself be run with ``python3.13t``, it can only attach to a ``python3.13t`` process or core file from another interpreter. (#206)
30
+
31
+
32
+ Bug Fixes
33
+ ~~~~~~~~~
34
+
35
+ - Fix a bug that was causing Python scripts executed directly via shebang to report the shell script as the executable. (#184)
36
+ - Heap corruption could cause PyStack to fail to generate a stack when ``--locals`` mode was used. This has been fixed by falling back to a reasonable default when attempting to format the repr of a local variable causes a dereference of an invalid pointer. (#194)
37
+ - Fix a crash when analysing processes where the eval loop has a shim frame at the bottom of the stack (#204)
38
+
39
+
11
40
  pystack 1.3.0 (2023-11-28)
12
41
  --------------------------
13
42
 
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.1
2
2
  Name: pystack
3
- Version: 1.3.0
3
+ Version: 1.4.1
4
4
  Summary: Analysis of the stack of remote python processes
5
5
  Home-page: https://github.com/bloomberg/pystack
6
6
  Author: Pablo Galindo Salgado
@@ -12,6 +12,7 @@ Classifier: Programming Language :: Python :: 3.9
12
12
  Classifier: Programming Language :: Python :: 3.10
13
13
  Classifier: Programming Language :: Python :: 3.11
14
14
  Classifier: Programming Language :: Python :: 3.12
15
+ Classifier: Programming Language :: Python :: 3.13
15
16
  Classifier: Programming Language :: Python :: Implementation :: CPython
16
17
  Classifier: Topic :: Software Development :: Debuggers
17
18
  Requires-Python: >=3.7.0
@@ -46,6 +46,7 @@ underlines = "-~"
46
46
  build = ["cp38-*", "cp39-*", "cp310-*", "cp311-*"]
47
47
  manylinux-x86_64-image = "manylinux2014"
48
48
  manylinux-i686-image = "manylinux2014"
49
+ musllinux-x86_64-image = "musllinux_1_1"
49
50
  skip = "*-musllinux_aarch64"
50
51
 
51
52
  [tool.cibuildwheel.linux]
@@ -115,3 +116,8 @@ omit = [
115
116
 
116
117
  [tool.coverage.report]
117
118
  show_missing = true
119
+
120
+ [tool.pytest.ini_options]
121
+ # pytest retains all temp files from the last 3 test suite runs by default.
122
+ # Keep only ones for failed tests to avoid filling up a disk.
123
+ tmp_path_retention_policy = "failed"
@@ -115,6 +115,7 @@ setuptools.setup(
115
115
  "Programming Language :: Python :: 3.10",
116
116
  "Programming Language :: Python :: 3.11",
117
117
  "Programming Language :: Python :: 3.12",
118
+ "Programming Language :: Python :: 3.13",
118
119
  "Programming Language :: Python :: Implementation :: CPython",
119
120
  "Topic :: Software Development :: Debuggers",
120
121
  ],
@@ -12,8 +12,11 @@ from typing import NoReturn
12
12
  from typing import Optional
13
13
  from typing import Set
14
14
 
15
+ from pystack import __version__
15
16
  from pystack.errors import InvalidPythonProcess
17
+ from pystack.process import decompress_gzip
16
18
  from pystack.process import is_elf
19
+ from pystack.process import is_gzip
17
20
 
18
21
  from . import errors
19
22
  from . import print_thread
@@ -116,6 +119,9 @@ def generate_cli_parser() -> argparse.ArgumentParser:
116
119
  parser.add_argument(
117
120
  "-v", "--verbose", action="count", default=0, dest="global_verbose"
118
121
  )
122
+ parser.add_argument(
123
+ "--version", action="version", version=__version__, help="Show version"
124
+ )
119
125
  parser.add_argument(
120
126
  "--no-color",
121
127
  action="store_true",
@@ -319,9 +325,32 @@ def process_core(parser: argparse.ArgumentParser, args: argparse.Namespace) -> N
319
325
  if not corefile.exists():
320
326
  parser.error(f"Core {corefile} does not exist")
321
327
 
328
+ if is_gzip(corefile):
329
+ corefile = decompress_gzip(corefile)
330
+
322
331
  if args.executable is None:
323
332
  corefile_analyzer = CoreFileAnalyzer(corefile)
324
333
  executable = pathlib.Path(corefile_analyzer.extract_executable())
334
+ if not executable.exists() or not is_elf(executable):
335
+ first_map = next(
336
+ (
337
+ map
338
+ for map in corefile_analyzer.extract_maps()
339
+ if map.path is not None
340
+ ),
341
+ None,
342
+ )
343
+ if (
344
+ first_map is not None
345
+ and first_map.path is not None
346
+ and first_map.path.exists()
347
+ and is_elf(first_map.path)
348
+ ):
349
+ executable = first_map.path
350
+ LOGGER.info(
351
+ "Setting executable automatically to the first map in the core: %s",
352
+ executable,
353
+ )
325
354
  if not executable.exists():
326
355
  raise errors.DetectedExecutableNotFound(
327
356
  f"Detected executable doesn't exist: {executable}"
@@ -1,3 +1,4 @@
1
+ #include <algorithm>
1
2
  #include <cassert>
2
3
  #include <cstring>
3
4
  #include <fstream>
@@ -160,13 +160,41 @@ typedef struct
160
160
  } PyCodeObject;
161
161
  } // namespace Python3_12
162
162
 
163
- typedef union {
164
- Python2::PyCodeObject v2;
165
- Python3_3::PyCodeObject v3_3;
166
- Python3_6::PyCodeObject v3_6;
167
- Python3_8::PyCodeObject v3_8;
168
- Python3_11::PyCodeObject v3_11;
169
- Python3_12::PyCodeObject v3_12;
163
+ namespace Python3_13 {
164
+ typedef uint16_t _Py_CODEUNIT;
165
+ typedef struct
166
+ {
167
+ PyObject_VAR_HEAD;
168
+ PyObject* co_consts;
169
+ PyObject* co_names;
170
+ PyObject* co_exceptiontable;
171
+ int co_flags;
172
+ int co_argcount;
173
+ int co_posonlyargcount;
174
+ int co_kwonlyargcount;
175
+ int co_stacksize;
176
+ int co_firstlineno;
177
+ int co_nlocalsplus;
178
+ int co_framesize;
179
+ int co_nlocals;
180
+ int co_ncellvars;
181
+ int co_nfreevars;
182
+ uint32_t co_version;
183
+ PyObject* co_localsplusnames;
184
+ PyObject* co_localspluskinds;
185
+ PyObject* co_filename;
186
+ PyObject* co_name;
187
+ PyObject* co_qualname;
188
+ PyObject* co_linetable;
189
+ PyObject* co_weakreflist;
190
+ void* co_executors;
191
+ void* _co_cached;
192
+ uintptr_t _co_instrumentation_version;
193
+ void* _co_monitoring;
194
+ int _co_firsttraceable;
195
+ void* co_extra;
196
+ char co_code_adaptive[1];
170
197
  } PyCodeObject;
198
+ } // namespace Python3_13
171
199
 
172
200
  } // namespace pystack
@@ -47,6 +47,11 @@ typedef struct
47
47
  PyObject** ma_values;
48
48
  } PyDictObject;
49
49
 
50
+ typedef struct _dictvalues
51
+ {
52
+ PyObject* values[1];
53
+ } PyDictValuesObject;
54
+
50
55
  } // namespace Python3
51
56
  namespace Python3_3 {
52
57
  typedef struct _dictkeysobject
@@ -77,8 +82,21 @@ typedef struct _dictkeysobject
77
82
  uint32_t dk_version;
78
83
  Py_ssize_t dk_usable;
79
84
  Py_ssize_t dk_nentries;
80
- char dk_indices[]; /* char is required to avoid strict aliasing. */
85
+ char dk_indices[1]; /* char is required to avoid strict aliasing. */
81
86
  } PyDictKeysObject;
82
87
  } // namespace Python3_11
83
88
 
89
+ namespace Python3_13 {
90
+
91
+ typedef struct _dictvalues
92
+ {
93
+ uint8_t capacity;
94
+ uint8_t size;
95
+ uint8_t embedded;
96
+ uint8_t valid;
97
+ PyObject* values[1];
98
+ } PyDictValuesObject;
99
+
100
+ } // namespace Python3_13
101
+
84
102
  } // namespace pystack
@@ -39,7 +39,7 @@ namespace Python3_7 {
39
39
  typedef struct _pyframeobject
40
40
  {
41
41
  PyObject_VAR_HEAD struct _pyframeobject* f_back;
42
- PyCodeObject* f_code;
42
+ PyObject* f_code;
43
43
  PyObject* f_builtins;
44
44
  PyObject* f_globals;
45
45
  PyObject* f_locals;
@@ -64,7 +64,7 @@ typedef signed char PyFrameState;
64
64
  typedef struct _pyframeobject
65
65
  {
66
66
  PyObject_VAR_HEAD struct _pyframeobject* f_back;
67
- PyCodeObject* f_code;
67
+ PyObject* f_code;
68
68
  PyObject* f_builtins;
69
69
  PyObject* f_globals;
70
70
  PyObject* f_locals;
@@ -126,12 +126,4 @@ typedef struct _interpreter_frame
126
126
 
127
127
  } // namespace Python3_12
128
128
 
129
- typedef union {
130
- Python2::PyFrameObject v2;
131
- Python3_7::PyFrameObject v3_7;
132
- Python3_10::PyFrameObject v3_10;
133
- Python3_11::PyFrameObject v3_11;
134
- Python3_12::PyFrameObject v3_12;
135
- } PyFrameObject;
136
-
137
129
  } // namespace pystack
@@ -82,9 +82,4 @@ struct _gc_runtime_state
82
82
  };
83
83
 
84
84
  } // namespace Python3_8
85
-
86
- typedef union {
87
- struct Python3_7::_gc_runtime_state v3_7;
88
- struct Python3_8::_gc_runtime_state v3_8;
89
- } GCRuntimeState;
90
85
  } // namespace pystack
@@ -247,13 +247,95 @@ typedef struct _is
247
247
  } PyInterpreterState;
248
248
  } // namespace Python3_12
249
249
 
250
- typedef union {
251
- Python2::PyInterpreterState v2;
252
- Python3_5::PyInterpreterState v3_5;
253
- Python3_7::PyInterpreterState v3_7;
254
- Python3_8::PyInterpreterState v3_8;
255
- Python3_9::PyInterpreterState v3_9;
256
- Python3_11::PyInterpreterState v3_11;
257
- Python3_12::PyInterpreterState v3_12;
250
+ namespace Python3_13 {
251
+
252
+ struct _pythreadstate; /* Forward */
253
+ struct PyMutex
254
+ {
255
+ uint8_t v;
256
+ };
257
+ typedef int (*_Py_pending_call_func)(void*);
258
+ struct _pending_call
259
+ {
260
+ _Py_pending_call_func func;
261
+ void* arg;
262
+ int flags;
263
+ };
264
+ struct _pending_calls
265
+ {
266
+ void* handling_thread;
267
+ PyMutex mutex;
268
+ int32_t npending;
269
+ int32_t max;
270
+ int32_t maxloop;
271
+ struct _pending_call calls[300];
272
+ int first;
273
+ int next;
274
+ };
275
+
276
+ struct _ceval_state
277
+ {
278
+ uintptr_t instrumentation_version;
279
+ int recursion_limit;
280
+ struct _gil_runtime_state* gil;
281
+ int own_gil;
282
+ struct _pending_calls pending;
283
+ };
284
+
285
+ struct _import_state
286
+ {
287
+ PyObject* modules;
288
+ PyObject* modules_by_index;
289
+ PyObject* importlib;
290
+ int override_frozen_modules;
291
+ int override_multi_interp_extensions_check;
292
+ int dlopenflags;
293
+ PyObject* import_func;
294
+ struct
295
+ {
296
+ PyThread_type_lock mutex;
297
+ unsigned long thread;
298
+ int level;
299
+ } lock;
300
+ struct
301
+ {
302
+ int import_level;
303
+ int64_t accumulated;
304
+ int header;
305
+ } find_and_load;
306
+ };
307
+
308
+ typedef struct _is
309
+ {
310
+ struct _ceval_state ceval;
311
+ struct _is* next;
312
+
313
+ int64_t id;
314
+ int64_t id_refcount;
315
+ int requires_idref;
316
+ PyThread_type_lock id_mutex;
317
+ long _whence;
318
+ int _initialized;
319
+ int _ready;
320
+ int finalizing;
321
+ uintptr_t last_restart_version;
322
+ struct pythreads
323
+ {
324
+ uint64_t next_unique_id;
325
+ _pythreadstate* head;
326
+ _pythreadstate* main;
327
+ Py_ssize_t count;
328
+ size_t stacksize;
329
+ } threads;
330
+ struct pyruntimestate* runtime;
331
+ void* _finalizing;
332
+ unsigned long _finalizing_id;
333
+ struct Python3_8::_gc_runtime_state gc;
334
+ // Dictionary of the sys module
335
+ PyObject* sysdict;
336
+ // Dictionary of the builtins module
337
+ PyObject* builtins;
338
+ struct _import_state imports;
258
339
  } PyInterpreterState;
340
+ } // namespace Python3_13
259
341
  } // namespace pystack
@@ -205,12 +205,6 @@ typedef struct _typeobject
205
205
  } PyTypeObject;
206
206
  } // namespace Python3_8
207
207
 
208
- typedef union {
209
- Python2::PyTypeObject v2;
210
- Python3_3::PyTypeObject v3_3;
211
- Python3_8::PyTypeObject v3_8;
212
- } PyTypeObject;
213
-
214
208
  /* These flags are used to determine if a type is a subclass. */
215
209
  constexpr long Pystack_TPFLAGS_INT_SUBCLASS = 1ul << 23u;
216
210
  constexpr long Pystack_TPFLAGS_LONG_SUBCLASS = 1ul << 24u;
@@ -105,13 +105,15 @@ struct _ceval_runtime_state
105
105
  struct _gil_runtime_state gil;
106
106
  };
107
107
 
108
+ struct PyThreadState;
109
+
108
110
  typedef struct pyruntimestate
109
111
  {
110
112
  int preinitializing;
111
113
  int preinitialized;
112
114
  int core_initialized;
113
115
  int initialized;
114
- PyThreadState* finalizing;
116
+ void* finalizing;
115
117
 
116
118
  struct pyinterpreters
117
119
  {
@@ -171,7 +173,7 @@ typedef struct pyruntimestate
171
173
  int preinitialized;
172
174
  int core_initialized;
173
175
  int initialized;
174
- PyThreadState* finalizing;
176
+ void* finalizing;
175
177
 
176
178
  struct pyinterpreters
177
179
  {
@@ -246,12 +248,187 @@ typedef struct pyruntimestate
246
248
  } PyRuntimeState;
247
249
  } // namespace Python3_12
248
250
 
251
+ namespace Python3_13 {
252
+
253
+ typedef struct _Py_DebugOffsets
254
+ {
255
+ char cookie[8];
256
+ uint64_t version;
257
+ uint64_t free_threaded;
258
+ // Runtime state offset;
259
+ struct _runtime_state
260
+ {
261
+ uint64_t size;
262
+ uint64_t finalizing;
263
+ uint64_t interpreters_head;
264
+ } runtime_state;
265
+
266
+ // Interpreter state offset;
267
+ struct _interpreter_state
268
+ {
269
+ uint64_t size;
270
+ uint64_t id;
271
+ uint64_t next;
272
+ uint64_t threads_head;
273
+ uint64_t gc;
274
+ uint64_t imports_modules;
275
+ uint64_t sysdict;
276
+ uint64_t builtins;
277
+ uint64_t ceval_gil;
278
+ uint64_t gil_runtime_state;
279
+ uint64_t gil_runtime_state_enabled;
280
+ uint64_t gil_runtime_state_locked;
281
+ uint64_t gil_runtime_state_holder;
282
+ } interpreter_state;
283
+
284
+ // Thread state offset;
285
+ struct _thread_state
286
+ {
287
+ uint64_t size;
288
+ uint64_t prev;
289
+ uint64_t next;
290
+ uint64_t interp;
291
+ uint64_t current_frame;
292
+ uint64_t thread_id;
293
+ uint64_t native_thread_id;
294
+ uint64_t datastack_chunk;
295
+ uint64_t status;
296
+ } thread_state;
297
+
298
+ // InterpreterFrame offset;
299
+ struct _interpreter_frame
300
+ {
301
+ uint64_t size;
302
+ uint64_t previous;
303
+ uint64_t executable;
304
+ uint64_t instr_ptr;
305
+ uint64_t localsplus;
306
+ uint64_t owner;
307
+ } interpreter_frame;
308
+
309
+ // Code object offset;
310
+ struct _code_object
311
+ {
312
+ uint64_t size;
313
+ uint64_t filename;
314
+ uint64_t name;
315
+ uint64_t qualname;
316
+ uint64_t linetable;
317
+ uint64_t firstlineno;
318
+ uint64_t argcount;
319
+ uint64_t localsplusnames;
320
+ uint64_t localspluskinds;
321
+ uint64_t co_code_adaptive;
322
+ } code_object;
323
+
324
+ // PyObject offset;
325
+ struct _pyobject
326
+ {
327
+ uint64_t size;
328
+ uint64_t ob_type;
329
+ } pyobject;
330
+
331
+ // PyTypeObject object offset;
332
+ struct _type_object
333
+ {
334
+ uint64_t size;
335
+ uint64_t tp_name;
336
+ uint64_t tp_repr;
337
+ uint64_t tp_flags;
338
+ } type_object;
339
+
340
+ // PyTuple object offset;
341
+ struct _tuple_object
342
+ {
343
+ uint64_t size;
344
+ uint64_t ob_item;
345
+ uint64_t ob_size;
346
+ } tuple_object;
347
+
348
+ // PyList object offset;
349
+ struct _list_object
350
+ {
351
+ uint64_t size;
352
+ uint64_t ob_item;
353
+ uint64_t ob_size;
354
+ } list_object;
355
+
356
+ // PyDict object offset;
357
+ struct _dict_object
358
+ {
359
+ uint64_t size;
360
+ uint64_t ma_keys;
361
+ uint64_t ma_values;
362
+ } dict_object;
363
+
364
+ // PyFloat object offset;
365
+ struct _float_object
366
+ {
367
+ uint64_t size;
368
+ uint64_t ob_fval;
369
+ } float_object;
370
+
371
+ // PyLong object offset;
372
+ struct _long_object
373
+ {
374
+ uint64_t size;
375
+ uint64_t lv_tag;
376
+ uint64_t ob_digit;
377
+ } long_object;
378
+
379
+ // PyBytes object offset;
380
+ struct _bytes_object
381
+ {
382
+ uint64_t size;
383
+ uint64_t ob_size;
384
+ uint64_t ob_sval;
385
+ } bytes_object;
386
+
387
+ // Unicode object offset;
388
+ struct _unicode_object
389
+ {
390
+ uint64_t size;
391
+ uint64_t state;
392
+ uint64_t length;
393
+ uint64_t asciiobject_size;
394
+ } unicode_object;
395
+
396
+ // GC runtime state offset;
397
+ struct _gc
398
+ {
399
+ uint64_t size;
400
+ uint64_t collecting;
401
+ } gc;
402
+ } _Py_DebugOffsets;
403
+
404
+ typedef struct pyruntimestate
405
+ {
406
+ _Py_DebugOffsets debug_offsets;
407
+ int _initialized;
408
+ int preinitializing;
409
+ int preinitialized;
410
+ int core_initialized;
411
+ int initialized;
412
+ PyThreadState* finalizing;
413
+ unsigned long _finalizing_id;
414
+
415
+ struct pyinterpreters
416
+ {
417
+ PyMutex mutex;
418
+ PyInterpreterState* head;
419
+ PyInterpreterState* main;
420
+ int64_t next_id;
421
+ } interpreters;
422
+ } PyRuntimeState;
423
+
424
+ } // namespace Python3_13
249
425
  typedef union {
250
426
  Python3_7::PyRuntimeState v3_7;
251
427
  Python3_8::PyRuntimeState v3_8;
252
428
  Python3_9::PyRuntimeState v3_9;
253
429
  Python3_11::PyRuntimeState v3_11;
254
430
  Python3_12::PyRuntimeState v3_12;
431
+ Python3_13::PyRuntimeState v3_13;
255
432
  } PyRuntimeState;
256
433
 
257
434
  } // namespace pystack
@@ -12,11 +12,13 @@ typedef uint8_t Py_UCS1;
12
12
  typedef Py_UCS4 Py_UNICODE;
13
13
  typedef Py_ssize_t Py_hash_t;
14
14
 
15
+ namespace Python3 {
15
16
  typedef struct
16
17
  {
17
18
  PyObject_VAR_HEAD Py_hash_t ob_shash;
18
19
  char ob_sval[1];
19
20
  } PyBytesObject;
21
+ } // namespace Python3
20
22
 
21
23
  namespace Python2 {
22
24
  typedef struct
@@ -37,19 +39,21 @@ typedef struct
37
39
 
38
40
  namespace Python3 {
39
41
 
42
+ struct _PyUnicode_State
43
+ {
44
+ unsigned int interned : 2;
45
+ unsigned int kind : 3;
46
+ unsigned int compact : 1;
47
+ unsigned int ascii : 1;
48
+ unsigned int ready : 1;
49
+ unsigned int : 24;
50
+ };
51
+
40
52
  typedef struct
41
53
  {
42
54
  PyObject_HEAD Py_ssize_t length;
43
55
  Py_hash_t hash;
44
- struct
45
- {
46
- unsigned int interned : 2;
47
- unsigned int kind : 3;
48
- unsigned int compact : 1;
49
- unsigned int ascii : 1;
50
- unsigned int ready : 1;
51
- unsigned int : 24;
52
- } state;
56
+ _PyUnicode_State state;
53
57
  wchar_t* wstr;
54
58
  } PyASCIIObject;
55
59
 
@@ -76,19 +80,13 @@ typedef struct
76
80
 
77
81
  namespace Python3_12 {
78
82
 
83
+ using Python3::_PyUnicode_State;
84
+
79
85
  typedef struct
80
86
  {
81
87
  PyObject_HEAD Py_ssize_t length;
82
88
  Py_hash_t hash;
83
- struct
84
- {
85
- unsigned int interned : 2;
86
- unsigned int kind : 3;
87
- unsigned int compact : 1;
88
- unsigned int ascii : 1;
89
- unsigned int ready : 1;
90
- unsigned int : 24;
91
- } state;
89
+ _PyUnicode_State state;
92
90
  } PyASCIIObject;
93
91
 
94
92
  typedef struct
@@ -100,6 +98,7 @@ typedef struct
100
98
 
101
99
  typedef struct
102
100
  {
101
+ PyCompactUnicodeObject _base;
103
102
  union {
104
103
  void* any;
105
104
  Py_UCS1* latin1;
@@ -110,10 +109,4 @@ typedef struct
110
109
 
111
110
  } // namespace Python3_12
112
111
 
113
- typedef union {
114
- Python2::PyUnicodeObject v2;
115
- Python3::PyUnicodeObject v3;
116
- Python3_12::PyUnicodeObject v3_12;
117
- } PyUnicodeObject;
118
-
119
112
  } // namespace pystack