Repository navigation
fix(pyutils): raise on cudaFuncSetAttribute and launch errors in bind_kernel - #215
Open
TanishGudise wants to merge 1 commit into
Open
TanishGudise wants to merge 1 commit into
TanishGudise wants to merge 1 commit into
Conversation
…_kernel Co-Authored-By: Claude Opus 5.5 <[email protected]>
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.
kittens::py::bind_kernelignores the result ofcudaFuncSetAttributeand never checks the launch. When a launch can't run (dynamic shared memory above the device's opt-in limit, an invalid block size, or a module with no code for the current GPU), the Python call returns normally and the output buffers are left untouched.Repro
A minimal binding: one
gl<float, 1, 1, -1, -1>output, which the Python side pre-fills with NaN, with dynamic shared memory and threads per block passed in.TKis a ThunderKittens checkout:On main,
fillandtorch.cuda.synchronize()both return andoutis still NaN. With this branch,fillraises:Results
H100 80GB HBM3, driver 595.91.07, nvcc 13.0, built as above (nvcc's default static cudart), 20 calls per case:
RuntimeError: fill: cudaFuncSetAttribute(MaxDynamicSharedMemorySize=233472) failed: invalid argumentRuntimeError: fill: kernel launch failed: invalid argumentRuntimeError: fill: cudaFuncSetAttribute(MaxDynamicSharedMemorySize=<smem>) failed: no kernel image is available for execution on the device, before the launch* Built with nvcc 12.8.93 and
-gencode arch=compute_100a,code=sm_100a, otherwise as above.Megakernels' low-latency Llama-1B demo behaves the same with and without this branch (20 runs each): no run with all-"!" output, one megakernel launch per step, median step 0.949 ms (main) vs 0.948 ms (this branch). Setup: head of HazyResearch/Megakernels#14, which pins this repo at 67845f5, built with nvcc 13.0 and
-gencode arch=compute_90a,code=sm_90a. The Makefile's-arch=sm_90adoesn't build on CUDA 13; see HazyResearch/Megakernels#10. Output varies from run to run in both builds (5 and 7 distinct outputs in 20 runs).I ran these on 2026-10-23 against 67845f5, and
mainhasn't moved since, so I reused those results rather than re-running them. On 2026-10-26 I checked that the repro still compiles againstmainand this branch with nvcc 12.8.93 and 13.4.92 for sm_90a (compile only, no warnings).Change
bind_kernelnow checks both calls. On failure it throwsstd::runtime_error(pybind11 turns it intoRuntimeError) with the binding name and the CUDA error string. A failedcudaFuncSetAttributethrows before the launch and clears the error it set. The binding name is copied into the lambda, so the message doesn't depend on the lifetime of thenameargument.Notes
C10_CUDA_KERNEL_LAUNCH_CHECK, thecudaGetLastError()check also picks up an error left pending by earlier CUDA work in the same runtime. That includes a sticky fault from an earlier kernel (e.g. an illegal memory access), which would now be raised here, under this binding's name.-lcudart_static), nothing else in the process sees the error; that's the setup measured above. If the extension shares PyTorch's libcudart, the error stays pending and can surface at PyTorch's next launch check, under the wrong operation. I haven't tested that case.bind_kernel. In-tree kernels uselaunch_kernelfromtorchutils.cuh, which already wraps both calls inCUDACHECK(print andexit), or launch directly. The callers are downstream projects such as Megakernels, which pins an older revision and would get this only after a submodule bump.AI disclosure: I used Claude while writing this fix and its repro; I reviewed every line, ran the tests on a rented GPU, and can answer questions about any of it.