#1945 release and adoption capability matrix
What #1945 has actually placed in the hands of a downstream consumer of this repository, at the pinned revisions recorded in §1. This is the U5 record: capability-specific release statements, the guidance that names each capability, and the adoption gates that follow from them.
1. Pinned revisions this matrix describes
| Repository | Revision |
|---|---|
tensor4all/tenferro-rs |
main at 7f3094ae8 (#2093); later upstream commits are tests, docs and examples only |
tensor4all/cubecl (fork) |
release/t4a-cubecl-0.11.0 at 8aeafdf50cb3db65cc727e4ab303ed5b504c5ab9 (the 0.10.2 line’s #27/#28/#29 superseded by 0.11) |
tensor4all/cubek (fork) |
release/t4a-cubek-0.3.0 at a1a106096a09fd27e1fbe9dbd2253d244f2df677 |
tensor4all/tensor4all-rs |
main at 11f29ff0 (tenferro pin ff94aeded…), with the B1 frontend surface |
“Released” below means merged with its gates green, not “planned”. The fork rows name the release branches those revisions belong to; each is published as t4a-cubecl* 0.11.0 and t4a-cubek* 0.3.0, which is what the workspace now requires.
Pin state and the cubecl 0.11 decision (2026-10-12)
Resolved by the 0.11 migration (#2132), and superseded by the dependency move that followed: the fork releases t4a-cubecl* 0.11.0 and t4a-cubek* 0.3.0 are published, and the workspace now requires those versions from crates.io, so no git pin remains and check-git-pin-content.py reports nothing. The measurements below are the record of why the port was needed. At the time, scripts/check-git-pin-content.py failed on main: t4a-cubecl 0.10.2 was republished from a different commit (eb2c8894…) whose content is upstream 0.10.2 without the fork patches, so the pinned 1811309… and the registry archive no longer agree. Measured options:
- pinning the republished
eb2c8894…satisfies the content check but drops the fork patches (ComputeClient::check_errorsdisappears), so the workspace does not build; - pinning the fork’s
release/t4a-cubecl-0.11.0(8aeafdf5…, published as 0.11.0) satisfies the content check and is the coherent pin, but upstream 0.11 reorganized the public API (cubecl::Runtime,cubecl::client::ComputeClient,cubecl::prelude::{ArrayArg,StorageType},cubecl::stream_id,cubecl_runtime::server::ComputeServer) andtenferro-gpureports 565 errors (390E0277, 83E0425, 50E0107, 21E0432, 17E0405) - a port, not a one-line bump; - the one-revision-per-graph rule requires the
cubekpin to move to a revision that pins cubecl 0.11.0 first (release/t4a-0.2.2pins 0.10.2, cubekmainpins 0.10.0).
An existing worktree branch migration/cubecl-0.11-upstream already carries 60 commits of that migration. Until the port lands, U4-2a and U4-2b are pinned at 1811309… and the content check stays red for reasons outside those slices.
2. Capability matrix
| Capability | State | Evidence | Downstream milestone |
|---|---|---|---|
| Held CPU session (U1) — caller-owned concrete session, ownership/entry proof, no hidden session entry | released | #2053, held-session tests | tensor4all-rs CPU backend/coexistence milestone (#866, #873) |
docs/guides/dispatch-and-engine-cost.md) | same milestone; the explicit frontend’s dispatch route |Held CUDA session (U3) — held reservation, typed reentry/contention, logical
StreamId capture, no per-op flush, Drop does not flush | released, then replaced by the caller-held CUDA engine (#2206) | #2059, 7 A100 tests, 3 compile-fail fixtures; the held-session design record is retired to execution-engine-ownership.md, guide #2071 | tensor4all-rs CUDA/async milestone |Owning pending transfers (U4 items 2–3) —
download_pending / upload_pending, admission that returns the package on refusal and retains on unproven enqueue, bounded retirement queue, no wait in Drop | released | #2061, #2065, #2073, #2076, docs/design/{asynchronous-transfer,owning-pending-transfers}-1945-u4.md, transfer bench #2066 | CUDA/async milestone; the only route that moves a value without host export/import |Source publication (U4 item 1, source half) — a produced value published with its producer frontier; the session, backend handle and source tensor may go away; the publication owns the value, its allocation address and readiness | released | #2101,
crates/tenferro-gpu/tests/source_publication.rs (7 A100 tests), 2 compile-fail fixtures, docs/design/source-publication-1945-u4.md (revision 5) | CUDA/async milestone |Cubecl-side boundary changes —
check_errors publication boundary (#27), bounded staging retention on the write path (#28), write authority required for server writes (#29) | released in the fork | fork PRs, docs/design/cubecl-fork-exit-1945.md | prerequisite for the routes above; #27 retired by the 0.11 migration (upstream reports failed launches on the affected buffers) — docs/design/cubecl-011-check-errors-disposition.md; #28/#29 not yet proposed upstream |Optional held AD adapter (U2-AD) | deferred, not solved | upstream design record D12; our measurement puts session entry at ≈5% of a 13.5 µs op, so the measured-signal precondition is unmet | must not be advertised; B3 depends on it |
Consumer copy of a published value (U4-2a) — same-runtime, same-device device-side copy with the pending-transfer ownership model | implemented and measured (
docs/design/consumer-copy-1945-u4-2a.md): exact-instance runtime eligibility before the captured-stream entry, wait_event + copy_bytes + recorded completion on the consumer’s captured stream, an owned typed destination, PendingRead ownership, and PublicationError::CopyRejected | 3 A100 tests (cross-stream copy with exact bytes, ordering behind a pending chained frontier, another-runtime refusal with the publication returned), 2 fault-injection tests, a trybuild exclusion fixture, and the unchanged source_publication/pending_* suites | CUDA/async milestone; claims bounded to the same runtime instance and device |Registry-authorized consumer read (U4-2b) — a published value read from another event domain through a registry-bound admission | out of scope under the current domain model (
docs/design/consumer-read-handoff-1945-u4-2.md): the native CUDA adapter fixes one provider target per device and a second registration with that target is rejected, so the two distinct event domains the capability needs cannot exist in one configuration; revisiting it needs either cross-epoch admission semantics or a registration/domain-model change | four pre-implementation reviews rejected the cross-runtime designs, and the axis-1 narrowing was then falsified on the registration rule | must not be advertised; cross-runtime and cross-device reads are unsupported as well |Direct-required / allow-staging route policy, P2P capability registration | declared non-goal for now (
docs/design/asynchronous-transfer-1945-u4.md: “No cross-domain/P2P route, no staging policy enum, no caller-output alias, no AD transfer”). A missing route is already a typed error (MissingTransferProvider { source_endpoint, destination_endpoint }), and PeerCopy/SameDeviceAsyncCopy exist as device-capability flags (crates/tenferro-gpu/src/cubecl/identity.rs) that no route uses | route inventory only | P2P is dropped for now: the machine has one A100, so no second device exists to verify a device-to-device route; a staging policy would need its own design and a consumer that asks for it |Multiple CUDA devices in one configuration | allowed by the registration rule (the provider target is per provider and device ordinal, and only a duplicate target is rejected), not verified here: the local machine has one A100 and no suite registers a second ordinal |
crates/tenferro-gpu/src/cubecl/runtime_adapter.rs (device:<ordinal>), crates/tenferro-runtime/src/runtime/snapshot.rs (DuplicateProviderDeviceTarget) | usable for placement/execution only: with no device-to-device route, values still move between devices through the host |Producer/consumer overlap | measured | #2106, the
transfer_overlap group in crates/tenferro-gpu/benches/transfer_paths.rs (controlled schedule) | measured claim only |Cross-stream readiness, host-wait-free publication, fault-injected terminal paths | not established | every transfer/publication test uses the ambient captured stream; the host bridge is still the only cross-domain route | claims must stay bounded until measured |
Differentiated (AD) transfer | not implemented | #1945 transfer contract item 6 | separate work; must not be implied by
detach |3. Guidance that names the capability set
| Document | Names |
|---|
docs/guides/engines-and-transfers.md | the caller-held CUDA engine, the pending transfer routes, what is not claimed (no fake async, no hidden waits) |execution-engine-ownership.md | what the caller-held CUDA engine submits, and the raw scope that replaced the held session |
docs/design/{asynchronous-transfer,owning-pending-transfers}-1945-u4.md | admission, refusal, retention and teardown contracts for transfers |docs/design/source-publication-1945-u4.md | the publication contract and every claim it declines to make |docs/design/cubecl-fork-exit-1945.md | which substrate changes the fork carries, which stay upstream, and the own-backend contingency |4. Adoption gates
- CPU milestone. A consumer that only needs held concrete CPU execution can adopt at the revisions in §1 without waiting for CUDA, transfer or AD work: the compatibility (eager) frontend and the explicit frontend build against the same revision, with no signature, storage or ABI rewrite and no second dependency version.
- CUDA/async milestone. Adoption includes the held CUDA session and the owning pending transfers. Source publication is part of it (#2101 merged).
- Per pin update. Both downstream frontends (compatibility/eager and explicit) are checked against the new revision, together with the CUDA test partition and the held-session / pending-transfer / publication tests.
- Not a gate. Universal application migration and removal of the global defaults are not required for any gate above, and no gate claims that held CPU sessions alone complete the CPU/GPU architecture.
5. What this matrix refuses to claim
- No capability marked deferred, unmeasured or not implemented may be described as released, and none is reachable through the public API as if it were.
- The pending routes add a route; they do not reroute the blocking transfer APIs, which stay blocking and keep their documented readiness.
- The fork’s changes are released in the fork. Until they are proposed and accepted upstream, they are not part of cubecl’s own story, and #1945’s residue there is described in
docs/design/cubecl-fork-exit-1945.mdrather than claimed as fixed.