| 325 | } |
| 326 | |
| 327 | PyThread::GCStatus |
| 328 | PyThread::calculateGCStatus( |
| 329 | Structure<py_thread_v>& ts, |
| 330 | const std::shared_ptr<const AbstractProcessManager>& manager) const |
| 331 | { |
| 332 | LOG(DEBUG) << "Attempting to determine GC Status"; |
| 333 | |
| 334 | remote_addr_t gcstate_addr; |
| 335 | if (manager->versionIsAtLeast(3, 9)) { |
| 336 | auto is_addr = ts.getField(&py_thread_v::o_interp); |
| 337 | Structure<py_is_v> interp(manager, is_addr); |
| 338 | gcstate_addr = interp.getFieldRemoteAddress(&py_is_v::o_gc); |
| 339 | } else if (manager->versionIsAtLeast(3, 7)) { |
| 340 | remote_addr_t pyruntime = manager->findSymbol("_PyRuntime"); |
| 341 | if (!pyruntime) { |
| 342 | LOG(DEBUG) << "Failed to get GC status because the _PyRuntime symbol is unavailable"; |
| 343 | return GCStatus::COLLECTING_UNKNOWN; |
| 344 | } |
| 345 | Structure<py_runtime_v> runtime(manager, pyruntime); |
| 346 | gcstate_addr = runtime.getFieldRemoteAddress(&py_runtime_v::o_gc); |
| 347 | } else { |
| 348 | LOG(DEBUG) << "GC Status retrieval not supported by this Python version"; |
| 349 | return GCStatus::COLLECTING_UNKNOWN; |
| 350 | } |
| 351 | |
| 352 | Structure<py_gc_v> gcstate(manager, gcstate_addr); |
| 353 | auto collecting = gcstate.getField(&py_gc_v::o_collecting); |
| 354 | LOG(DEBUG) << "GC status correctly retrieved: " << collecting; |
| 355 | return collecting ? GCStatus::COLLECTING : GCStatus::NOT_COLLECTING; |
| 356 | } |
| 357 | |
| 358 | // Create a similar funciton which does not pass the pointer to thread state, only the manager and the |
| 359 | // tid |
nothing calls this directly
no test coverage detected