-
Notifications
You must be signed in to change notification settings - Fork 47
Description
Summary
The LLVM SPIR-V backend (llc from SPIRV_LLVM_Backend_jll) crashes with LLVM ERROR: Broken function found, compilation aborted! when compiling GPU kernels that call functions returning small static array types like SMatrix{1,1,Float32}.
The root cause is that SMatrix{1,1,Float32} gets lowered to LLVM type [1 x float], and the SPIR-V backend incorrectly transforms the return type to i32 during internal passes, causing the LLVM IR verifier to abort.
MWE
using OpenCL, pocl_jll, KernelAbstractions, StaticArrays
# A kernel that calls a function returning SMatrix{1,1,Float32}
# This gets lowered to `[1 x float]` in LLVM IR, which the SPIR-V backend miscompiles
@kernel function smatrix_return_kernel(out)
i = @index(Global)
A = SMatrix{1,1,Float32}(3.0f0)
B = SMatrix{1,1,Float32}(2.0f0)
C = A * B # returns SMatrix{1,1,Float32}
out[i] = C[1]
end
backend = OpenCL.OpenCLBackend()
out = KernelAbstractions.zeros(backend, Float32, 4)
kernel = smatrix_return_kernel(backend, 4)
kernel(out, ndrange=4)
KernelAbstractions.synchronize(backend)Error output
LLVM ERROR: Broken function found, compilation aborted!
ERROR: LoadError: Failed to translate LLVM code to SPIR-V.
...
caused by: failed process: Process(`...llc ...`, ProcessSignaled(6)) [0]
Context
This was discovered via SciML/DiffEqGPU.jl, where stiff ODE solvers using autodiff=false call finite_diff_jac, which returns SMatrix types. The finite_diff.jl tests fail on all Julia versions (lts, 1, pre) when using the OpenCL backend. See https://github.com/SciML/DiffEqGPU.jl/actions/runs/22247943080/job/64365791848
The same kernels work correctly with CUDA, AMDGPU, and JLArrays backends. They also likely work with the Khronos SPIR-V translator (SPIRV_LLVM_Translator_jll), since this is specifically a bug in the LLVM native SPIR-V backend.
Environment
- Julia: 1.10, 1.12, nightly (all affected)
- OpenCL.jl: latest (MQ6HZ)
- GPUCompiler.jl: latest (OCZFZ)
- SPIRV_LLVM_Backend_jll: v20.1.5+3
- pocl_jll (CPU OpenCL implementation)
Possibly related upstream
This appears related to LLVM's handling of struct/array return types in the SPIR-V backend. The SPIRV_LLVM_Backend_jll already carries patches for similar issues (e.g. fix_insertvalue.patch for LLVM#127977, atomic_cmpxchg_64bit.patch for LLVM#152863), but no patch exists yet for this specific struct-return miscompilation.