Skip to content

cuda.core: rename _resource_handles to _rt and split its C++ into _cpp/rt/ - #2837

Merged
Andy-Jost merged 6 commits into
NVIDIA:mainfrom
Andy-Jost:ajost/resource-handles-refactor
Sep 15, 2026
Merged

Andy-Jost merged 6 commits into
NVIDIA:mainfrom
Andy-Jost:ajost/resource-handles-refactor

Conversation

@Andy-Jost

@Andy-Jost Andy-Jost commented Sep 11, 2026

Copy link
Copy Markdown
Contributor

Description

cuda.core._resource_handles holds cuda.core's runtime support layer: the resource handles, the driver function-pointer table, the GIL and context guards, the error-reporting path, deferred cleanup, the handle registry and a few version-gated driver shims. This renames it to cuda.core._rt, moves its C++ under cuda/core/_cpp/rt/ in namespace cuda_core::rt, and splits the two monoliths (about 1,240 and 3,360 lines) into nine headers and twelve sources, one resource family per file, with the Python-coupled code behind a single header. Behavior does not change. One dead function and one dead constant go.

Every function keeps its body, signature and symbol name; only the namespace qualifier and the file it lives in move. The .pxd exposes the same declarations in the same order minus the dead function, and the 53 cimporting Cython files change only their cimport line. All of the C++ still compiles into the one _rt extension, so the shared state (registries, thread-local error slot, driver pointers, cleanup queue) keeps living in exactly one shared library.

Layout (cuda/core/_cpp/rt/): rt.hpp (umbrella, named only by _rt.pyx), handles.hpp (umbrella, named only by _rt.pxd; its closure is types.hpp and py.hpp), types.hpp (handle aliases, tagged values, Prepared* types, inline as_cu/as_intptr), api.hpp (every other prototype, one banner per family), driver_api.hpp/.cpp (the p_* table and version-gated shims), error.hpp/.cpp (thread-local error state, non-propagating reporting), py.hpp (the one file that includes <Python.h>: py_is_finalizing, the GIL guards, as_py, the PyObject* prototypes), context_scope.hpp and internal.hpp (helpers shared across files and never named from Cython, in cuda_core::rt::detail), py_report.cpp, py_deferred_cleanup.cpp, and context.cpp, stream.cpp, event.cpp, memory.cpp, program.cpp, graph.cpp, graph_exec.cpp, texture.cpp. driver_api.cpp and error.cpp compile with no Python include path. The three design notes move with the code.

Build. Every extension lists the headers under _cpp/<stem>/ as depends, because a cimporting extension compiles against the copy of handles.hpp that cythonize places in its build directory, and the copy needs its siblings beside it. build_ext now compiles the sources of every extension through one shared thread pool (setuptools compiles an extension's sources serially and parallelizes only across extensions), so the twelve translation units add no wall-clock time.

Commits. The series is built to be reviewed step by step: rename with no code motion; remove the dead py_object_user_object_destroy; build hooks; header split; source split (with tests/test_rt_layout.py); docs.

Verification.

  • The split is generated, not hand-edited: an anchor-based generator cuts the two monoliths into fragments and emits every file as boilerplate (SPDX, includes, namespace braces, // Implemented in lines, the few new declarations) plus verbatim ranges; its check mode regenerates from the pre-split revision and compares with the files in the tree. After cuda.core: define the error handling policy and report failures that cannot be raised #2759 merged, the series was regenerated on main the same way rather than merged by hand, and the result differs from the previously approved head by exactly cuda.core: define the error handling policy and report failures that cannot be raised #2759's final changes carried into the split files.
  • The dynamic symbol table of _rt equals the old module's under s/cuda_core::/cuda_core::rt::/, minus the removed function, plus exactly the ten helpers promoted from anonymous namespaces to cuda_core::rt::detail and the err object.
  • __pyx_capi__ has the same 104 keys with the same signatures.
  • Consumers changed on cimport lines only (checked with a whole-diff filter).
  • test_rt_layout.py pins the seam rules: <Python.h> only in py.hpp, bare sibling includes that exist, umbrellas named only by their Cython file, the consumer closure with nothing that has storage, and no .pxd-declared function called by its own name inside _rt.pyx.
  • Full cuda.core test suite on a GPU system with a matched CUDA 13.4 toolkit and cuda-bindings 13.4.1: 4273 passed, 122 skipped, 3 xfailed. The one failure, system/test_system_device.py::test_device_cpu_affinity, comes from NVML reporting an empty CPU set for the GPUs of that machine and does not involve this code. (An environment pairing 13.1 headers with cuda-bindings 13.2 fails the 14 copy-options tests on this branch and on main alike; that is cuda-core: require a cuda-bindings version floor at build and run time #2783's "guards disable working features", not this change.) cu12 and Windows through CI.

Checklist

  • New or existing tests cover these changes.
  • The documentation is up to date with these changes.

🤖 Generated with Claude Code

@Andy-Jost Andy-Jost added this to the cuda.core 1.3.0 milestone Sep 11, 2026
@Andy-Jost Andy-Jost added enhancement Any code-related improvements cuda.core Everything related to the cuda.core module labels Sep 11, 2026
@copy-pr-bot

copy-pr-bot Bot commented Sep 11, 2026

Copy link
Copy Markdown
Contributor

Auto-sync is disabled for draft pull requests in this repository. Workflows must be run manually.

Contributors can view more details about this message here.

@Andy-Jost Andy-Jost self-assigned this Sep 11, 2026
@github-actions github-actions Bot added the CI/CD CI/CD infrastructure label Sep 11, 2026
@Andy-Jost

Copy link
Copy Markdown
Contributor Author

/ok to test

@github-actions

Copy link
Copy Markdown
Contributor

@Andy-Jost

Copy link
Copy Markdown
Contributor Author

/ok to test

@Andy-Jost
Andy-Jost force-pushed the ajost/resource-handles-refactor branch from 2161c01 to 7ee9c1f Compare September 14, 2026 16:40
@Andy-Jost Andy-Jost changed the title cuda.core: rename _resource_handles to _rt and split its C++ into _cpp/rt/ [stacked on #2759, #2799] cuda.core: rename _resource_handles to _rt and split its C++ into _cpp/rt/ [stacked on #2759] Sep 14, 2026

@mdboom mdboom left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Other than the one thing (which would break my workflow, at least), LGTM.

Comment thread cuda_core/build_hooks.py
Listing the whole directory keeps the rule free of include parsing; the
cost is that every extension rebuilds when any of these headers changes,
exactly as editing the one monolithic header did before the split."""
cpp = Path("cuda", "core", "_cpp")

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This will break if building from anywhere but cuda_core.

Suggested change
cpp = Path("cuda", "core", "_cpp")
cpp = Path(__file__).parent / "cuda" / "core" / "_cpp"

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I forgot to include this. I will make a follow-up PR right after this merges.

The module holds cuda.core's runtime support layer: resource handles, the
driver function-pointer table, error reporting and deferred cleanup. Rename
it to _rt and move its C++ under _cpp/rt/ in namespace cuda_core::rt. Every
function keeps its body, signature and symbol name; only the namespace
qualifier and the file names change.

- git mv _resource_handles.{pyx,pxd,pyi} to _rt.*; resource_handles.{hpp,cpp}
  to _cpp/rt/rt.{hpp,cpp}; the three design notes to _cpp/rt/.
- The 53 cimporting Cython files change only their cimport line.
- Delete _CUDA_DRIVER_API_V1_NAME, a capsule-name constant nothing reads.
- Regenerate the stub (stubgen-pyx).

The dynamic symbol table of the built extension equals the old one under
s/cuda_core::/cuda_core::rt::/, and __pyx_capi__ has the same keys.
A Py_DECREF callback shaped for cuUserObjectCreate, superseded by the
make_opaque_py ownership path and called from nowhere. Its four
declarations go: the C++ prototype and body, the .pxd cdef and the .pyx
extern declaration.
…sion's sources in parallel

Two build changes the C++ split needs.

Every extension now lists the headers under cuda/core/_cpp/<stem>/ as
`depends`. A cimporting extension compiles against the header its .pxd
names, and cythonize copies each `depends` entry into its build directory,
so the copied header finds its sibling includes beside it. Listing the whole
directory avoids parsing includes; every extension rebuilds when one of
these headers changes, exactly as editing the one monolithic header did.

setuptools compiles the sources of one extension serially and parallelizes
only across extensions, so a multi-source extension becomes the critical
path. build_ext now fans the per-object compile calls of every extension
out to one shared thread pool of `nthreads` workers. MSVC keeps the stock
path.
The monolithic header becomes: types.hpp (handle aliases, tagged values,
Prepared* types, the inline as_cu/as_intptr accessors), py.hpp (the one file
that includes <Python.h>: py_is_finalizing, make_py and as_py, and the
prototypes that take or return PyObject*), driver_api.hpp (the p_* table and
the version-gated shims), error.hpp (thread-local error state and the
non-propagating reporting API), api.hpp (every other prototype, one banner
per resource family), plus two umbrellas: rt.hpp, named only by _rt.pyx,
and handles.hpp, named only by _rt.pxd, whose include closure is types.hpp
and py.hpp.

Every declaration moves verbatim; the only additions are the file
boilerplate, one banner in py.hpp and `// Implemented in <file>` lines on
the prototypes whose body lives outside their family source. The generator
(anchored on the monolith's text) and its check mode live in the
maintainer's notes; the dynamic symbol table and __pyx_capi__ of the built
extension are unchanged.
The monolithic source becomes twelve translation units: one resource family
per file (context, stream, event, memory, program, graph, graph_exec,
texture), the driver table with its version-gated shims (driver_api.cpp),
the error state and non-propagating reporting (error.cpp), and the two
Python-coupled bodies (py_report.cpp, py_deferred_cleanup.cpp). Two headers
hold the helpers the files share and Cython never names, in namespace
cuda_core::rt::detail: context_scope.hpp (enter/restore/exit_context and
the invoke_in_context templates) and internal.hpp (HandleRegistry,
WarnOnFailure with the pw_* wrappers, DeallocationStream,
DeferredCleanupItem and the declarations of the promoted helpers). py.hpp
gains the GIL guards; error.hpp declares the thread-local `err` that
error.cpp now defines.

Every definition moves verbatim. Helpers that were static or in an anonymous
namespace and are now called across files become external with a
declaration; everything local to one file keeps its anonymous namespace.
driver_api.cpp and error.cpp compile without a Python include path.

Verification: the generator's check mode reproduces all 21 files from the
monoliths; the dynamic symbol table gains exactly the nine promoted
detail:: functions and the err object and loses nothing; __pyx_capi__ is
unchanged. tests/test_rt_layout.py pins the layout rules.
DESIGN.md, GRAPH_ATTACHMENTS.md and REGISTRY_DESIGN.md moved with the code;
this keeps them from misleading: the module name, the file layout, the
cdef extern examples, and the heading that still named the deleted
_CUDA_DRIVER_API_V1 capsule. AGENTS.md learns the directory form of
_cpp/<name>/ and the new paths. One release note for the renamed private
module and its shipped .pxd.
@Andy-Jost
Andy-Jost force-pushed the ajost/resource-handles-refactor branch from 7ee9c1f to c61a5b5 Compare September 15, 2026 18:57
@Andy-Jost Andy-Jost changed the title cuda.core: rename _resource_handles to _rt and split its C++ into _cpp/rt/ [stacked on #2759] cuda.core: rename _resource_handles to _rt and split its C++ into _cpp/rt/ Sep 15, 2026
@Andy-Jost
Andy-Jost marked this pull request as ready for review September 15, 2026 18:57
@Andy-Jost
Andy-Jost enabled auto-merge (squash) September 15, 2026 20:45
@Andy-Jost
Andy-Jost merged commit fe41350 into NVIDIA:main Sep 15, 2026
206 of 210 checks passed
github-actions Bot pushed a commit that referenced this pull request Sep 16, 2026
Removed preview folders for the following PRs:
- PR #2817
- PR #2837
- PR #2841
- PR #2852
- PR #2856
- PR #2863
@Andy-Jost
Andy-Jost deleted the ajost/resource-handles-refactor branch September 16, 2026 17:57
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

CI/CD CI/CD infrastructure cuda.core Everything related to the cuda.core module enhancement Any code-related improvements

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants