Repository navigation
Conversation
osabnis
force-pushed
the
gpu-fc-f16-zero-point
branch
from
October 14, 2026 18:44
2bad2f9 to
99e6e04
Compare
osabnis
force-pushed
the
gpu-fc-f16-zero-point
branch
from
October 19, 2026 17:22
6e18375 to
db59f59
Compare
…nt-rebase # Conflicts: # src/plugins/intel_gpu/include/intel_gpu/primitives/fully_connected.hpp # src/plugins/intel_gpu/src/graph/impls/onednn/fully_connected_onednn.cpp
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.
Details:
Improve GGUF quantization accuracy in the llama.cpp OpenVINO backend by preserving exact zero points for compressed FC layers on the oneDNN path.
GGUF Q4_K, Q4_1, Q5_1, and Q5_K weights use
w = d * q - m. Representing this asscale * (q - zp)requireszp = m / d, which is generally non-integer. Roundingzpintroduces systematic weight errors. This change uses oneDNN'squantization_mode::static_sbzpto computew = scale * q - zp', withzp' = zp * scale, preserving exact dequantization.Status: Draft; depends on oneDNN. Requires
quantization_mode::static_sbzp: RFC uxlfoundation/oneDNN#6218 (approved) and implementation uxlfoundation/oneDNN#6306 (in review). This branch does not build against OpenVINO's current oneDNN version; it can merge once #6306 is merged and the oneDNN submodule is updated. Related llama.cpp change: ravi9/llama.cpp#341.Accuracy
KL divergence against the llama.cpp CPU backend during decode at context 1024, measured on Intel Arc B390 (Panther Lake), Windows. Lower is better.
KL divergence improves by 3–23×, bringing OpenVINO within 1.3× of Vulkan on five of six models. Qwen3.5 4B performs better than Vulkan on this metric.
Phi-4 mini remains 3.6× above Vulkan. The remaining gap comes from the output layer, which llama.cpp's OpenVINO backend requantizes: keeping that layer in its original GGUF type reduces KL divergence to 0.0031. This is outside the scope of this change.
Implementation
prepare_quantization.cpp: For compressed FC layers with constant f16/bf16 scales and zero points, u4/i4/u8 weights, and at least two K groups, precomputezp * scaleon the host and setdecompression_zero_point_after_scale. Apply this only when oneDNN is enabled and supported on the device.fully_connected_onednn: Accept floating-point zero points when flagged and configurestatic_sbzp.Scaled zero points are written directly in the layout consumed by the FC:
[N, groups]parameters in fbyx, while[groups, N]parameters retain their layout. This avoids a reorder and temporary copy during program build.The transformation belongs in
prepare_quantization, rather than a graph transformation, becausezp * scaleis specific to the oneDNN implementation. Backend selection depends on device capabilities (including IMMAD support) and oneDNN availability. Applying it at graph level would also change the values consumed by OpenCL kernels, which subtract the zero point before scaling.Dynamic quantization
FCs with floating-point weight zero points are already excluded from dynamic quantization (
DynamicQuantizeFullyConnectedskips an unsupported weight zero-point type), so the FCs this change applies to keep f16/bf16 activations, whichstatic_sbzprequires. The check ondynamic_quantized_activationinprepare_quantizationis only a guard. The prefill numbers below include this: prefill stays within 2% of rounded integer zero points, which are eligible for dynamic quantization. Integer activations withstatic_sbzpare left for a later revision of the oneDNN RFC, driven by performance data.Tests
New coverage in
fully_connected_gpu_test.cpp,compressed_int{4,8}_f16_zp_*, includes:Validation
Tested on Intel Arc B390 (Panther Lake), Windows, using master
38ff87c030with the oneDNNstatic_sbzpimplementation (uxlfoundation/oneDNN#6306, prototype version at the time) in the submodule.*f16_zp*: 15/15 passed.*fully_connected*:*FullyConnected*: 1,282 passed, 0 failed.fully_connected_decompression_paramstest also passed 64/64.jit:gemm.Performance
llama-benchmedian tokens/s across three runs, rounded → exact zero points:Decode at depth 0 is 1–4% slower, partly because f16 zero points add about 8% to Q4_K weight bytes. Deep-context decode and prefill remain within 2% of the original performance. Without this change, exact zero points made prefill 2.2–2.9× slower in measurements taken before rebase. Run-to-run variation is approximately ±2% for deep-context decode and ±1% for prefill.
Peak GPU memory
Exact zero points increase peak GPU memory during decode at depth 4096 because f16 zero points are larger than u4 zero points, and original and scaled values coexist during program build.
#38995 uploads grouped FC scales in their final layout, reducing the additional memory required by this change.
Related changes
transpose_b_scaleandtranspose_b_zpfor[N, groups]versus[groups, N]parameters. This branch is rebased on that refactor. New tests cover[groups, N]parameters (compressed_int4_f16_zp_groups_major) with static and dynamic shapes.prepare_quantization.cpp; whichever merges second should not conflict on that change.Tickets:
AI Assistance: