fix(VT-REFTIER-HOST-ADDRESSABLE): the reference tier gated on unified memory, not on whether the host can address it (#844, #1435) - #1477
Merged
Conversation
…mory is unified, not whether the host can address it (#844, #1435) `ReferenceTierEligible` decides whether a device may receive the portable CPU reference tier, and it asks `Backend::UnifiedMemory()`. A host kernel does not need unified memory; it needs to be able to dereference what `Backend::Alloc` returned. `include/vt/backend.h` already records the difference beside `Backend::DeviceMemoryIsHostAddressable()`: CUDA on GB10 reports unified memory because host and device address the same physical RAM, and a plain `cudaMalloc` pointer is still not host-dereferenceable. So on GB10 every op with no native CUDA kernel installed the CPU host kernel, which then dereferenced device pointers. The process took SIGSEGV under a banner claiming a "correct but slow" fallback. Measured twice: `vt::QuantFp8Static` on sm_110 (#960), and `vt::MatmulFp8BlockScaled` on a CUTLASS-less CUDA build (#1435), which exits 139 with `test cases: 0 assertions: 0`. This commit is the spec only, committed before the implementation so the commit order proves the order of work. It argues the predicate swap, enumerates all five backends and shows that exactly one cell moves, rejects a copy-in/copy-out staging tier with reasons, and records the `vt_cuda_report_feature` half of #1435 under `## Owed` because it needs a CUDA configure this host cannot run. The issue index gains a row for #844, which had none. FOLLOWING_AGENTS_PROTOCOL Following-Agents-Protocol: true AI-Assisted: true Assisted-by: AGENT:claude-opus-5 [Claude Code]
… the host cannot address, instead of segfaulting on it (#844, #1435) `ReferenceTierEligible` now asks `Backend::DeviceMemoryIsHostAddressable()` instead of `Backend::UnifiedMemory()`. A CPU kernel dereferences the pointers `Backend::Alloc` returned, so host-addressability is the question it asks; unified memory is a wider property that does not imply it. `include/vt/backend.h` already carried the refutation beside the narrow predicate, and its default is `false` for exactly this reason. CUDA allocates with `cudaMalloc` and reports unified memory on GB10, so it used to be eligible. Every CUDA op without a native kernel therefore installed the CPU host kernel over device pointers, and the process took SIGSEGV under a banner claiming a correct fallback. It now refuses by name, and the refusal says which precondition the device failed. The banner names the property that permits it rather than asserting correctness in three words. Exactly one backend cell moves. Vulkan already overrides the narrow predicate; Metal (MTLResourceStorageModeShared) and ROCm (managed or pageable-access integrated allocations) gain a one-line override that returns the value they already report for unified memory, so both keep the tier and neither changes behaviour. Neither translation unit is compiled by CI or by this host, which is why each override is one line beside the existing `UnifiedMemory()` override in the same class. `tests/vt/test_reference_tier.cpp` reproduces the GB10 property pair without a GPU: a fake backend that reports unified memory and refuses host-addressability. The case requires that no provider installs, that `GetOp` throws rather than returning the CPU function pointer, and that the message names the op, the device and the reason. On the unfixed tree the tier installs 107 providers and `GetOp` returns the host kernel. `src/vt/cuda/cuda_attention_cross.cu` carried a header note whose premise this change removes: it said GB10 would have run the DiT's cross-attention on the host, "running, correct". That was never correct, and it is no longer possible. Comment only; the translation unit's code is untouched. FOLLOWING_AGENTS_PROTOCOL Following-Agents-Protocol: true AI-Assisted: true Assisted-by: AGENT:claude-opus-5 [Claude Code]
…rt is not one box and not one feature cell The `nvcc` compile check this row owed for its one comment-only `.cu` edit ran on `thor:gpu0` (NVIDIA Thor, CUDA 13.0 V13.0.88, aarch64), job `645bf395-23fc-408f-a9ad-b9823885622c`. It configured this branch at `817e1769c` with `-DVLLM_CPP_CUDA=ON -DVLLM_CPP_CUDA_ARCHITECTURES=121a` and no CUTLASS, and the configure reported `cutlass-nvfp4: ENABLED for [121a]` and `cutlass-fp8: ENABLED for [121a]`. #1435 measured that on `dgx:gpu0` for one feature cell. A second box and a second cell say the same thing, so the report is a property of `vt_cuda_report_feature` reading the architecture intersection before the CUTLASS detection, not a property of either host. Recorded under `## Owed`, where that half of #1435 already lives. FOLLOWING_AGENTS_PROTOCOL Following-Agents-Protocol: true AI-Assisted: true Assisted-by: AGENT:claude-opus-5 [Claude Code]
…ich property the gate reads The header of `tests/vt/test_reference_tier.cpp` states the three properties the file proves, and property 1 still named `Backend::UnifiedMemory()` as the safety gate. The gate now reads `Backend::DeviceMemoryIsHostAddressable()`, and the file asserts it against two fakes rather than one: the discrete backend it always had, and the GB10 pair added by this row. The header also now says why the new case uses its own device slot. A reference-tier provider cannot be uninstalled once registered, so a case that must observe an EMPTY provider table needs a table no other case has touched. Comment only. Rebuilt and rerun: 6 cases, 6 passed, 34 assertions, 34 passed, `Status: SUCCESS!`. FOLLOWING_AGENTS_PROTOCOL Following-Agents-Protocol: true AI-Assisted: true Assisted-by: AGENT:claude-opus-5 [Claude Code]
…rent already owns, and "exactly one cell moves" was wrong Five review findings, one of them a guaranteed red on a legitimate build. F1. `tests/vt/test_reference_tier.cpp` needed a device slot no other registrar had claimed, and took `kTENSTORRENT` on the belief that the enumerator was unused. It is not: `src/vt/tenstorrent/tenstorrent_ops.cpp` registers 21 op sites on it, `OpId::kRelu` among them, and `vllm` carries an INTERFACE `--whole-archive`, so on `-DVLLM_CPP_TENSTORRENT=ON` that registrar runs inside this test binary. The old `REQUIRE(OpProviderCount(kRelu, kSlot) == 0)` was described in a comment as failing loudly if something were wrong. Nothing has to be wrong: it fails unconditionally on a supported configuration no CI lane builds, so it would have landed as a permanent red for whoever next turned that backend on, and `RegisterBackend` would have displaced a live backend on the way. Measured both ways here, with a scratch registrar reproducing what `--whole-archive` does. Before the guard: `6 cases | 1 failed`, `23 assertions | 1 failed`, `FAILURE!`, rc=1 — the same numbers the reviewer got. After the guard, same simulation: `6 cases | 6 passed`, `22 assertions`, `SUCCESS!`, rc=0, with the skip MESSAGE printed. `kXPU` is the only slot with no production registration and this case cannot share it, because a reference-tier provider cannot be uninstalled once registered. So the slot stays and the guard is what was missing. F2. `include/vt/backend.h` still described the tier as reading `UnifiedMemory()` in two places. That is the header a reader opens for exactly this distinction, so a stale sentence there is the defect this row exists to remove. F3. "Exactly one cell moves" was wrong. Vulkan moves too. Its `DeviceMemoryIsHostAddressable()` is unconditionally `true`, while its `UnifiedMemory()` is false where no combined host-visible, host-coherent, DEVICE_LOCAL memory type exists — `VulkanContext` then falls back to the host flags alone and `VT_CHECK`s that one was found. On such a device the tier was withheld before and is installed now. It is a widening, and it is sound because that `VT_CHECK` guarantees every allocation is host memory, not because a tier is harmless. The spec's Design table, its Risks item 1, and the comment in `op_provider.cpp` all said otherwise. F4. The pull request carries `Fixes #844`, which closes it, but two of that issue's four items are not done: the refusal names the op, the device and the failed precondition, not the BUILD FEATURE that would have supplied the kernel, and nothing warns at engine construction. The spec named #844 itself as owner of that remainder, so on close the pointer would have resolved to a closed issue and the work would be ownerless. Split into #1482, owned by this row, appended to the issue index, and referenced from `## Owed`. `Refs #844` with the issue left open was the alternative and is rejected: the defect in its title is fixed, and leaving it open would misreport that. F5. Three Mamba2 guards justified themselves with "`ReferenceTierEligible(kCUDA)` is TRUE ... `GetOp` does not throw". Both halves are now false. The guards are worth keeping — they still catch a run-time decline, and a future backend answering the narrow predicate true restores the hazard exactly — so each paragraph now reads as the reason the guard exists rather than as current behaviour, and says not to delete it. The spec also records the reachability mutation the reviewer ran and the implementer did not: deleting the refusal clause from the `VT_CHECK` inside `Resolve` reds `test_reference_tier.cpp`, so the new message is measured through `vt::GetOp` rather than by calling the helper. Focused suite after the repairs: 6 cases, 6 passed, 33 assertions, 33 passed, `SUCCESS!`. One assertion fewer than before, because the precondition REQUIRE became the skip guard. FOLLOWING_AGENTS_PROTOCOL Following-Agents-Protocol: true AI-Assisted: true Assisted-by: AGENT:claude-opus-5 [Claude Code]
`origin/main` advanced to `af25bd251` while this row held a full CI verdict at `b2c29e8f9`. Merge rather than rebase, so the reviewed SHAs and the verdict taken on them stay reachable. Three files are shared, and only one conflicted. `src/vt/op_provider.cpp` auto-merged, and the two changes are disjoint. #1497 added `kDflash2SelectorEdges` and `kTopKValuesIndices` to `OpNameImpl`; this row rewrites `ReferenceTierEligible`, adds `ReferenceTierRefusalReason`, and rewords the reference-tier banner. The merged file was reconstructed independently, by applying this row's diff to `origin/main`'s version, and is byte-identical to what git produced. Neither change weakens the other: the corrected predicate has exactly two call sites, `MaybeInstallReferenceTier` and `RegisterReferenceTier`, and #1497 adds no third. Both of its new ops register a native CUDA kernel (`cuda_ops.cu`, `cuda_sample.cu`), so neither reaches the reference tier on CUDA and the narrowed gate does not change their behaviour. `docs/USAGE.md` conflicted, and resolves to `origin/main`'s version byte for byte. This row edited the reference-tier paragraph inside `### A DISABLED feature removes its kernels, not the ops that do not need it`. #1491 retired that whole section: its migration manifest routes `docs/USAGE.md:168` to `docs/BUILD.md` as `deduplicated`, and `docs/BUILD.md` carries none of the prose, so the subject is retired from public documentation rather than moved. Re-applying the edit would resurrect a section a landed change deliberately removed. The correction this row owed that file is discharged by the deletion, because the false guidance it repaired no longer exists anywhere in `docs/`. `.agents/issue-index.md` union-merged. All 487 of `origin/main`'s rows are present byte for byte, this row contributes exactly its own two, and the header prose is identical to `origin/main`. The spec's `Why the banner's wording changes` paragraph said `docs/USAGE.md` quotes the three words the banner drops. The merge made that false, so the paragraph now says which change retired the quote. FOLLOWING_AGENTS_PROTOCOL Following-Agents-Protocol: true AI-Assisted: true Assisted-by: AGENT:claude-opus-5 [Claude Code]
This was referenced Aug 20, 2026
localai-bot
added a commit
that referenced
this pull request
Aug 21, 2026
…l and integrated ROCm, and its numbers do not (#1502) (#1620) `docs/ENVIRONMENT.md` described the lever's reach as "Vulkan today" and closed with "No effect on CUDA/CPU/Metal, whose backends do not advertise the property". Both halves stopped being true at `cffe59b02` (#1477). That change moved `ReferenceTierEligible` off the wider `UnifiedMemory()` onto `Backend::DeviceMemoryIsHostAddressable()`, and added truthful overrides so no backend silently lost the reference tier. `MetalBackend` now answers `MetalContext::unified_memory()` and `RocmBackend` answers its `unified_memory_`. The weight loader gates this lever on exactly that predicate, at both `AdoptDeviceBytesAsHost` branches in `qwen3_5_weights.cpp`, so the lever acts on Apple silicon and on an integrated ROCm part. The correction is not "add two backend names". Every number in that row is GB10 through Vulkan, and nobody has measured the lever on either new arm. The row read as if the measurement covered the reach, so it now says which backends it is MEASURED on and which merely satisfy the predicate. CUDA and CPU are unchanged and still inert: neither overrides the default `false`, which `tests/vllm/platforms/test_platform.cpp` pins for GB10, and the CPU backend reporting `UnifiedMemory() == true` while the narrower predicate stays `false` is the whole reason the two properties are separate. Verified against the tree rather than against the issue: the three overrides, the two gate sites, the absent CUDA and CPU overrides, and the GB10 assertion were each read at this head. The measurement on Metal and on integrated ROCm stays owed. It needs an Apple-silicon box or an integrated AMD part, which this row has not taken, so it is recorded under `## Owed` in the spec that widened the predicate rather than left to be discovered from a document that now promises less than it did. No checker relates a backend predicate to a prose sentence, and none can be built cheaply, which is why this landed as a document defect rather than a red gate. Fixes #1502 FOLLOWING_AGENTS_PROTOCOL Following-Agents-Protocol: true AI-Assisted: true Assisted-by: AGENT:claude-opus-5 [Claude Code] Co-authored-by: Ettore Di Giacinto <mudler@localai.io>
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
ReferenceTierEligibledecides whether a device may receive the portable CPUreference tier. It asked
Backend::UnifiedMemory(). A host kernel does not needunified memory; it needs to be able to dereference what
Backend::Allocreturned.
include/vt/backend.halready carried the refutation, beside thepredicate that asks the right question:
CudaBackend::AlloccallscudaMalloc. So every CUDA op without a nativekernel installed the CPU host kernel as a
vt-cpu-refprovider, that kerneldereferenced device pointers, and the process took SIGSEGV — after printing a
banner that claimed the opposite:
This is #844, measured twice on GB10:
vt::QuantFp8Staticonsm_110(#960),and
vt::MatmulFp8BlockScaledon a CUTLASS-less CUDA build (#1435), wheretests/vt/test_ops_matmul_fp8_block_cudaexits 139 withtest cases: 0 assertions: 0. The second is reachable on a default build:VLLM_CPP_CUTLASS_FETCHdefaultsOFFand CUTLASS is not a submodule.Why this got a row and a spec, and not an in-flow fix
The reference tier is shared dispatch. Every op that can fall back, on every
backend, resolves through this one predicate, so the blast radius is the whole
op table rather than one FP8 kernel.
.agents/issue-index.mdhad alreadyrecorded the same judgement on #1435 — "both are code changes on a CUDA path
needing their own row, spec and hardware re-gate" — and
.agents/specs/vt-fp8-quant-arch-gate.md## Outcomerecorded that #960deliberately did not take this on: "making the reference tier refuse ... is
#844's class, which is a larger change to the tier and is deliberately still
open".
So: row
VT-REFTIER-HOST-ADDRESSABLE, spec.agents/specs/vt-reference-tier-host-addressable.md,committed in
447cb5c9ebefore the implementation in817e1769c. The commitorder is the proof. The row is deliberately not added to an area matrix:
BACKEND-ACCEL-PROVIDERalready carries anACTIVErow for this seam, and asecond row would put a shared-file edit in the path of a one-predicate fix.
The change
ReferenceTierEligibleasksBackend::DeviceMemoryIsHostAddressable(). No newseam, no new virtual, and no
DeviceTypebranch — the audit's rule thateligibility never keys on the device type is kept.
Two backend cells move, and the spec enumerates all five to show which:
AlloccudaMallocMTLResourceStorageModeSharedhasUnifiedMemoryhipMallocCUDA loses the tier — that is the crash. Vulkan widens, and the first draft
of this description got that wrong by claiming only one cell moved.
VulkanBackend::DeviceMemoryIsHostAddressable()already returnedtrueunconditionally, while
UnifiedMemory()readsVulkanContext::unified_memory(),which is set from
FindMemoryType(mem, ~0u, kHostFlags | VK_MEMORY_PROPERTY_DEVICE_LOCAL_BIT) >= 0.Where no such combined type exists that is false, the context falls back to
FindMemoryType(mem, ~0u, kHostFlags)and thenVT_CHECKs that one was found.So on that device every allocation is host-visible and host-coherent anyway, and
a tier that used to be withheld is now installed. Sound because of that
VT_CHECK, not because a portable tier is harmless.Metal and ROCm gain a one-line override so they do not lose the tier as a side
effect. Both return the value those backends already report for unified memory,
so their behaviour is byte-identical. ROCm answers
unified_memory_rather thanmanaged_alloc_on purpose: the registrar setsunified_memory_ = managed_alloc || (pageable_memory_access && integrated), andboth branches give the host a pointer it may dereference — the first by the
hipMallocManagedcontract, the second by thePageableMemoryAccessattributethat the backend's own comment records as measured on gfx1151 and gfx1103.
Two messages change with it. The refusal names which precondition the device
failed, so a reader does not have to open
op_provider.cppto learn that aportable fallback exists and was withheld. The banner names the fact that makes
it valid instead of asserting correctness in three words — those three words are
what #844 quotes as having misled a reader past a
SIGSEGV.
Red first, then green
The condition is reproducible with no GPU: it is a property pair on a backend,
not a hardware event.
tests/vt/test_reference_tier.cppgains a fake backendthat reports
UnifiedMemory() == trueandDeviceMemoryIsHostAddressable() == false— the GB10 CUDA shape — on its owndevice slot, because a reference-tier provider cannot be uninstalled once
registered and the case must observe an empty table. That slot is skipped, not
asserted empty; see the review repairs below for why that distinction was a
must-fix.
RED, on the unfixed tree at
447cb5c9e(ANSI stripped, both lines read):Failing for the intended reason, not an incidental one:
107 host kernels installed for a device the host cannot address, and
GetOpreturned the CPU function pointer rather than throwing. That last assertion is
what separates a refusal from a fallback: the tier installs
src->fn, the verysame pointer, so an equal answer is the defect even when nothing throws.
GREEN, at
817e1769c:The rest of the suite
Full CPU build clean (
-Werror, 1130/1130,BUILD_RC=0, zeroerror:lines),then
ctest -j 6over the whole tree:That one is #1052, which the issue index already records at this exact
assertion —
tests/vllm/v1/test_engine_core_proc.cpp:481"searches for the abortframe over a FIXED bud[get]" and needs the parallel harness to reproduce. It is
not reachable from this change:
grep -c 'UnifiedMemory\|RegisterBackend\|ReferenceTier'over that test file is 0, so it registers no backend, and on a CPU-only
build
TryGetBackendreturnsnullptrfor every non-CPU device, which makes theold and new predicates return identically
false. Rerun standalone three timeshere:
SUCCESS,FAILURE,SUCCESS, with assertion counts of 109, 1104 and116 — a race, not a verdict. Another session was running its own
cteston thisbox at the same time.
The seam's own suites, run together afterwards:
test_reference_tier,test_op_provider,test_backend_cross_device(4 variants),test_backend_multidevice— 7/7 passed.Mutation
The fix mutated in a scratch copy — the predicate put back to
UnifiedMemory(),one line:
Both the diffstat and the compile result are printed because a mutation that
never applied and a mutation that failed to build each read as a passing test.
The tree was then restored and re-verified byte-for-byte:
sha256 e9ad9fd6e69124153b9bd34a2993c05f5442acaa8a507cb9437e0a463d711a39beforeand after, green again at 6/6 and 34/34.
The one
.cufile, compiled by a real nvccsrc/vt/cuda/cuda_attention_cross.cucarried a header note whose premise thischange removes: it said GB10 would have run the DiT's cross-attention on the
host, "running, correct, and making 'the forward ran on the GPU' false". It was
never correct — the host kernel dereferences device pointers — and after this
change it is not possible. The edit is comment-only.
Comment-only is not a licence to skip nvcc here, so it did not:
rc run -d thor:gpu0, job645bf395-23fc-408f-a9ad-b9823885622c, NVIDIA Thor,CUDA 13.0 V13.0.88, aarch64. Configure with
-DVLLM_CPP_CUDA=ON -DVLLM_CPP_CUDA_ARCHITECTURES=121aand no CUTLASS, then the single object:The postcondition is asserted, not inferred from
rc=0: the object exists andcarries
sm_121aSASS.A second, unplanned measurement
That same configure printed, on a build containing no CUTLASS at all:
#1435 measured that on
dgx:gpu0for one feature cell. A second box and asecond cell make it a property of
vt_cuda_report_featurereading thearchitecture intersection before the CUTLASS detection, not a property of either
host. Recorded in
## Owedby7c07270b6, where that half of #1435 lives.Fresh review: five findings, all repaired in
b2c29e8f9F1, and it was a must-fix. The new case took
kTENSTORRENTbelieving theenumerator was unused. It is not:
src/vt/tenstorrent/tenstorrent_ops.cppregisters 21 op sites on it,
OpId::kReluamong them, andvllmcarries anINTERFACE
--whole-archive, so on-DVLLM_CPP_TENSTORRENT=ONthat registrarruns inside this test binary. The old
REQUIRE(OpProviderCount(kRelu, kSlot) == 0)was commented as failing loudly if something were wrong. Nothing has to be wrong:
it fails unconditionally on a supported configuration no CI lane builds, so it
would have landed as a permanent red for whoever next enabled that backend, and
RegisterBackendwould have displaced a live backend on the way.Verified here both ways, with a scratch static registrar reproducing what
--whole-archivedoes:(a) reproduces the reviewer's numbers exactly. The tree was restored
byte-for-byte afterwards (
sha256 0735aeb9…f02741b) and rebuilt green. The slotitself stays:
kXPUis the only DeviceType with no production registration andthis case cannot share it, because a reference-tier provider cannot be
uninstalled once registered. What was missing was the guard, not a different
slot.
F2.
include/vt/backend.hstill described the tier as readingUnifiedMemory(), at theFlushPending()comment and atTryGetBackend. Thatis the header a reader opens for exactly this distinction.
F3. "Exactly one cell moves" was wrong; corrected above, in the spec's
Design table and Risks item 1, and in the comment in
op_provider.cpp.F4. Split the remainder of #844 into #1482 rather than leaving it owned by an
issue this PR closes. Reasoning under Issues below.
F5. Three Mamba2 guards justified themselves with "
ReferenceTierEligible(kCUDA)is TRUE …
GetOpdoes not throw". Both halves are now false. The guards areworth keeping — they still catch a run-time decline, and a future backend
answering the narrow predicate
truerestores the hazard exactly — so eachparagraph now reads as the reason the guard exists, and says not to delete it.
Comment-only; suites unchanged and green:
test_ops_mamba2_ssd8/8 · 1175 assertions,test_ops_mamba2_state_update6/6 ·2469,
test_ops_mamba2_gated_norm9/9 · 2107.Reachability, run by the reviewer and not by me. Deleting the refusal clause
from the
VT_CHECKinsideResolve— the production path everyvt::GetOptakes — reds
test_reference_tier.cpp. So the new message is measured through aproduction entry point, not by calling the helper directly. Recorded in the
spec's gates, because "nothing lands dead" asks for exactly this.
Focused suite after the repairs: 6 cases, 6 passed, 33 assertions, 33 passed,
Status: SUCCESS!— one assertion fewer than the 34 quoted above, because theprecondition
REQUIREbecame the skip guard. Seam suites re-run together: 8/8.What this does NOT claim
Nothing about the block-wise FP8 arm. It has no token gate, no speed claim,
and its correctness is established only on the seven shapes actually run under
#1437. This change turns one crash into one named refusal and claims nothing
else about that arm.
No CUDA run. The defect was measured on GB10 and the fix is verified on the
host tier against a fake backend carrying the exact property pair. A CUDA re-run
of
tests/vt/test_ops_matmul_fp8_block_cudaon a CUTLASS-less build, to recordthe refusal replacing exit 139, is owed by this row and named in the spec.
Metal and ROCm are not compiled anywhere this change can reach. CI has no
macOS or ROCm job and this host has neither toolchain. That is why each override
is one line, placed beside the existing
UnifiedMemory()override in the sameclass, returning a value those backends already compute.
Issues
Fixes #844.
#1435 stays OPEN, deliberately. Its
vt_cuda_report_featurehalf needs a CUDAconfigure and is listed under
## Owedin this row's spec, with the thorreproduction above.
#1482 is new, and it is why
Fixes #844is safe. Two of #844's four "what donelooks like" items are not done here: item 1 also wants the refusal to name the
BUILD FEATURE that would have supplied the kernel (the landed message names the
op, the device and the failed precondition, not
this build has no cutlass-fp8), and item 4 wants a warning at engine construction rather thanonly at configure time. The spec originally named #844 itself as the owner of
that remainder, which would have pointed at a closed issue the moment this
merged. #1482 carries it, owned by this row, indexed, and referenced from
## Owed.That sentence and the one above are worded to keep a closing keyword away from
every number except 844: PR #1155 auto-closed issue #584 from inside ordinary
prose.
NOTE ON THE MERGE.
docs/USAGE.mdis absent from this change's file list.It carried the same misleading guidance and was going to be corrected here,
but #1491 RETIRED that section outright rather than relocating it -- its
migration manifest routes it to
docs/BUILD.mdasdeduplicated, and noprose matching
correct but slow,portable CPU fallbackorNO native kernelsurvives anywhere underdocs/. Re-applying the edit would haveresurrected deleted content, so the file resolves to
origin/mainbyte forbyte and the debt is discharged by the deletion.
FOLLOWING_AGENTS_PROTOCOL
Following-Agents-Protocol: true
AI-Assisted: true
Assisted-by: AGENT:claude-opus-5 [Claude Code]