25extern void gemv_q4_k_q8_k(
float *y,
const void *W,
const void *x_q8,
int M,
int K);
27 float *
C,
int M,
int N,
int K);
30extern void gemv_q6_k_q8_k(
float *y,
const void *W,
const void *x_q8,
int M,
int K);
32 float *
C,
int M,
int N,
int K);
35extern void gemm_nt_q8_0_q8_0(
const void *A_q8,
const void *B_q8,
const float *bias,
36 float *
C,
int M,
int N,
int K);
39extern void gemm_nt_q5_0_q8_0(
const void *A_q8,
const void *B_q5,
const float *bias,
40 float *
C,
int M,
int N,
int K);
43extern void gemv_q5_0(
float *y,
const void *W,
const float *x,
int M,
int K);
44extern void gemv_q8_0(
float *y,
const void *W,
const float *x,
int M,
int K);
47extern void gemv_q5_0_q8_0(
float *y,
const void *W,
const void *x_q8,
int M,
int K);
48extern void gemv_q8_0_q8_0(
float *y,
const void *W,
const void *x_q8,
int M,
int K);
60 float *output,
float *rstd_cache,
61 int tokens,
int d_model,
int aligned_embed_dim,
float eps);
65 const float *cos_cache,
const float *sin_cache,
66 int num_heads,
int num_kv_heads,
int num_tokens,
67 int head_dim,
int aligned_head_dim,
int pos_offset);
69 int max_seq_len,
int head_dim,
float base,
70 int rotary_dim,
const char *scaling_type,
71 float scaling_factor);
74extern void swiglu_forward(
const float *input,
float *output,
int tokens,
int dim);
78 const float *q,
const float *k,
const float *v,
float *output,
79 int num_heads,
int num_kv_heads,
int num_tokens,
80 int head_dim,
int aligned_head_dim,
int kv_stride_tokens);
94 const float *packed_qg,
111 const float *packed_qkv,
123 const float *dt_bias,
130 const float *state_in,
148 const float *packed_qkv,
181 const float *state_in,
221 const float *input_f32,
243 const float *input_f32,
264 const float *input_f32,
278 for (
int r = 0; r < rows; r++) output[r] = 0.0f;
292 const float *input_f32,
306 for (
int r = 0; r < rows; r++) output[r] = 0.0f;
320 const float *input_f32,
332 for (
int r = 0; r < rows; r++) output[r] = 0.0f;
346 const float *input_f32,
358 for (
int r = 0; r < rows; r++) output[r] = 0.0f;
376 const void *input_q8_k,
385 const void *input_q8_k,
407 const void *input_q8_0,
423 const void *input_q8_0,
435 const float *input_f32,
437 int rows,
int cols,
int n_tokens)
440 int n_blocks_per_row = cols /
CK_QK_K;
443 memset(output, 0, n_tokens * rows *
sizeof(
float));
448 for (
int t = 0; t < n_tokens; t++) {
450 q8_data + t * n_blocks_per_row, cols);
468 const float *input_f32,
470 int rows,
int cols,
int n_tokens)
473 int n_blocks_per_row = cols /
CK_QK_K;
476 memset(output, 0, n_tokens * rows *
sizeof(
float));
481 for (
int t = 0; t < n_tokens; t++) {
483 q8_data + t * n_blocks_per_row, cols);
501 const float *input_f32,
503 int rows,
int cols,
int n_tokens)
506 int n_blocks_per_row = cols /
CK_QK8_0;
509 memset(output, 0, n_tokens * rows *
sizeof(
float));
514 for (
int t = 0; t < n_tokens; t++) {
516 q8_data + t * n_blocks_per_row, cols);
534 const float *input_f32,
536 int rows,
int cols,
int n_tokens)
539 int n_blocks_per_row = cols /
CK_QK8_0;
542 memset(output, 0, n_tokens * rows *
sizeof(
float));
547 for (
int t = 0; t < n_tokens; t++) {
549 q8_data + t * n_blocks_per_row, cols);
568 int n_tokens,
int dim,
float eps)
576 int n_tokens,
int n_heads,
int n_heads_kv,
int head_dim,
577 int pos_offset,
float theta)
580 int half_dim = head_dim / 2;
581 int max_seq = pos_offset + n_tokens;
583 float *cos_cache = (
float *)malloc(max_seq * half_dim *
sizeof(
float));
584 float *sin_cache = (
float *)malloc(max_seq * half_dim *
sizeof(
float));
585 if (!cos_cache || !sin_cache) {
592 head_dim,
"none", 1.0f);
597 float *q_reorder = (
float *)malloc(n_heads * n_tokens * head_dim *
sizeof(
float));
598 float *k_reorder = (
float *)malloc(n_heads_kv * n_tokens * head_dim *
sizeof(
float));
600 if (q_reorder && k_reorder) {
602 for (
int t = 0; t < n_tokens; t++) {
603 for (
int h = 0; h < n_heads; h++) {
604 for (
int d = 0; d < head_dim; d++) {
605 q_reorder[h * n_tokens * head_dim + t * head_dim + d] =
606 q[t * n_heads * head_dim + h * head_dim + d];
612 for (
int t = 0; t < n_tokens; t++) {
613 for (
int h = 0; h < n_heads_kv; h++) {
614 for (
int d = 0; d < head_dim; d++) {
615 k_reorder[h * n_tokens * head_dim + t * head_dim + d] =
616 k[t * n_heads_kv * head_dim + h * head_dim + d];
623 cos_cache, sin_cache,
624 n_heads, n_heads_kv, n_tokens,
625 head_dim, head_dim, pos_offset);
628 for (
int t = 0; t < n_tokens; t++) {
629 for (
int h = 0; h < n_heads; h++) {
630 for (
int d = 0; d < head_dim; d++) {
631 q[t * n_heads * head_dim + h * head_dim + d] =
632 q_reorder[h * n_tokens * head_dim + t * head_dim + d];
637 for (
int t = 0; t < n_tokens; t++) {
638 for (
int h = 0; h < n_heads_kv; h++) {
639 for (
int d = 0; d < head_dim; d++) {
640 k[t * n_heads_kv * head_dim + h * head_dim + d] =
641 k_reorder[h * n_tokens * head_dim + t * head_dim + d];
654 int n_tokens,
int n_heads,
int n_heads_kv,
int head_dim,
655 int pos_offset,
float theta)
663 float *inv_freq = (
float *)malloc((head_dim / 2) *
sizeof(float));
664 if (!inv_freq)
return;
666 for (
int i = 0; i < head_dim / 2; i++) {
667 inv_freq[i] = 1.0f / powf(theta, (
float)(2 * i) / head_dim);
671 for (
int t = 0; t < n_tokens; t++) {
672 int pos = pos_offset + t;
673 for (
int h = 0; h < n_heads; h++) {
674 float *qh = q + t * n_heads * head_dim + h * head_dim;
676 for (
int i = 0; i < head_dim / 2; i++) {
677 float freq = pos * inv_freq[i];
678 float cos_val = cosf(freq);
679 float sin_val = sinf(freq);
682 float x0 = qh[i * 2];
683 float x1 = qh[i * 2 + 1];
684 qh[i * 2] = x0 * cos_val - x1 * sin_val;
685 qh[i * 2 + 1] = x0 * sin_val + x1 * cos_val;
691 for (
int t = 0; t < n_tokens; t++) {
692 int pos = pos_offset + t;
693 for (
int h = 0; h < n_heads_kv; h++) {
694 float *kh = k + t * n_heads_kv * head_dim + h * head_dim;
696 for (
int i = 0; i < head_dim / 2; i++) {
697 float freq = pos * inv_freq[i];
698 float cos_val = cosf(freq);
699 float sin_val = sinf(freq);
701 float x0 = kh[i * 2];
702 float x1 = kh[i * 2 + 1];
703 kh[i * 2] = x0 * cos_val - x1 * sin_val;
704 kh[i * 2 + 1] = x0 * sin_val + x1 * cos_val;
714 int n_tokens,
int intermediate_dim)
722 float max_val = input[0];
723 for (
int i = 1; i < n; i++) {
724 if (input[i] > max_val) max_val = input[i];
729 for (
int i = 0; i < n; i++) {
730 output[i] = expf(input[i] - max_val);
735 float inv_sum = 1.0f / sum;
736 for (
int i = 0; i < n; i++) {
737 output[i] *= inv_sum;
746 const float *state_in,
775 ssm_conv1d_forward(conv_x, kernel, out, kernel_size, num_channels, num_tokens, num_seqs);
802 const float *dt_bias,
825 state_in, q, k, v, conv_x, state_out, history_len, num_seqs, num_tokens, q_dim, k_dim, v_dim);
900 num_heads, num_kv_heads, tokens,
913 const float *attn_out,
914 const float *residual,
915 const float *ln2_gamma,
916 const void *wo,
const float *bo,
int wo_dt,
917 const void *w1,
const float *b1,
int w1_dt,
918 const void *w2,
const float *b2,
int w2_dt,
921 int aligned_embed_dim,
923 int aligned_head_dim,
924 int intermediate_dim,
925 int aligned_intermediate_dim,
931 int aligned_embed_dim,
933 int aligned_head_dim,
934 int aligned_intermediate_dim);
960 const float *attn_out,
961 const float *residual,
962 const float *ln2_gamma,
976 const int CK_DT_Q5_0_VAL = 11;
977 const int CK_DT_Q4_K_VAL = 7;
978 const int CK_DT_Q6_K_VAL = 8;
981 int aligned_embed_dim = embed_dim;
982 int aligned_head_dim = head_dim;
983 int aligned_intermediate = intermediate;
986 if ((intermediate % 256) != 0) {
987 aligned_intermediate = ((intermediate + 255) / 256) * 256;
992 tokens, aligned_embed_dim, num_heads, aligned_head_dim, aligned_intermediate);
994 void *scratch = malloc(scratch_size);
1005 wo, NULL, CK_DT_Q5_0_VAL,
1006 w1, NULL, CK_DT_Q5_0_VAL,
1007 w2, NULL, w2_is_q6k ? CK_DT_Q6_K_VAL : CK_DT_Q4_K_VAL,
1014 aligned_intermediate,
void ck_test_quantize_q8_k(const float *src, void *dst, int n)
Quantize FP32 to Q8_K (for activations)
void dequant_q4_0_row(const void *src, float *dst, size_t n_elements)
Dequantize Q4_0 row (multiple blocks)
void attention_forward_causal_head_major_gqa_flash_strided(const float *q, const float *k, const float *v, float *output, int num_heads, int num_kv_heads, int num_tokens, int head_dim, int aligned_head_dim, int kv_stride_tokens)
void ck_test_gemm_q4_k(const void *weight_q4k, const float *input_f32, float *output, int rows, int cols, int n_tokens)
Q4_K GEMM - batched matrix multiply with quantized weights.
int ck_get_block_q8_k_size(void)
Get Q8_K block size in bytes.
void ck_test_dequant_q6_k(const void *src, float *dst, int n)
Dequantize Q6_K data to FP32.
void ck_test_rope(float *q, float *k, int n_tokens, int n_heads, int n_heads_kv, int head_dim, int pos_offset, float theta)
RoPE (Rotary Position Embedding)
void ck_test_recurrent_silu(const float *x, float *out, int rows, int dim)
Apply SiLU elementwise to recurrent rows.
void recurrent_qk_l2_norm_forward(float *q, float *k, int rows, int q_dim, int k_dim, int head_dim, float eps)
void swiglu_forward(const float *input, float *output, int tokens, int dim)
void ck_test_recurrent_dt_gate(const float *alpha, const float *dt_bias, const float *a, float *gate, int rows, int dim)
Transform recurrent alpha rows into the DeltaNet gate.
void ck_test_gated_deltanet_autoregressive(const float *q, const float *k, const float *v, const float *g, const float *beta, const float *state_in, float *state_out, float *out, int num_heads, int state_dim, float norm_eps)
Gated DeltaNet autoregressive update.
void ck_test_attn_gate_sigmoid_mul(const float *x, const float *gate, float *out, int rows, int dim)
Multiply attention output rows by sigmoid(gate) elementwise.
void ck_test_split_q_gate(const float *packed_qg, float *q, float *gate, int rows, int q_dim, int gate_dim, int group_dim)
Split a packed full-attention Q+gate matrix into Q rows and gate rows.
void ck_test_gemv_q5_0_q8_0(const void *weight_q5_0, const float *input_f32, float *output, int rows, int cols)
Q5_0 x Q8_0 quantized GEMV - matches llama.cpp's approach.
void ck_test_recurrent_conv_state_update(const float *state_in, const float *q, const float *k, const float *v, float *conv_x, float *state_out, int history_len, int num_seqs, int num_tokens, int q_dim, int k_dim, int v_dim)
Build the recurrent convolution input history window.
void gemv_q8_0(float *y, const void *W, const float *x, int M, int K)
Auto-dispatch GEMV for Q8_0 weights based on CPU features.
void ck_test_recurrent_split_conv_qkv(const float *packed_qkv, float *q, float *k, float *v, int rows, int q_dim, int k_dim, int v_dim)
Split the post-convolution recurrent packed QKV rows.
void ck_test_dequant_q4_0(const void *src, float *dst, int n)
Dequantize Q4_0 data to FP32.
void ck_test_softmax(const float *input, float *output, int n)
Softmax (simple, non-causal)
void ck_test_rmsnorm(const float *input, const float *weight, float *output, int n_tokens, int dim, float eps)
RMSNorm.
void gemv_q5_0_q8_0(float *y, const void *W, const void *x_q8, int M, int K)
Matrix-vector multiply with Q5_0 weights and Q8_0 input.
void attn_gate_sigmoid_mul_forward(const float *x, const float *gate, float *out, int rows, int num_heads, int state_dim)
void recurrent_split_conv_qkv_forward(const float *packed_qkv, float *q, float *k, float *v, int rows, int q_dim, int k_dim, int v_dim)
void recurrent_conv_state_update_forward(const float *state_in, const float *q, const float *k, const float *v, float *conv_x, float *state_out, int history_len, int num_seqs, int num_tokens, int q_dim, int k_dim, int v_dim)
void gemv_q5_0(float *y, const void *W, const float *x, int M, int K)
Auto-dispatch GEMV for Q5_0 weights based on CPU features.
void ck_test_gemm_q5_0(const void *weight_q5_0, const float *input_f32, float *output, int rows, int cols, int n_tokens)
Test Q5_0 x Q8_0 GEMM (batch matrix multiply)
void ck_test_dequant_q4_k(const void *src, float *dst, int n)
Dequantize Q4_K data to FP32.
void ck_test_attention_causal(const float *q, const float *k, const float *v, float *out, int num_heads, int num_kv_heads, int tokens, int seq_len, int head_dim)
Multi-head causal attention for prefill (head-major layout)
void ck_test_gemv_q4_k(const void *weight_q4k, const float *input_f32, float *output, int cols)
Q4_K GEMV - dot product of quantized weights and FP32 input.
void mega_fused_outproj_mlp_prefill(float *output, const float *attn_out, const float *residual, const float *ln2_gamma, const void *wo, const float *bo, int wo_dt, const void *w1, const float *b1, int w1_dt, const void *w2, const float *b2, int w2_dt, int tokens, int embed_dim, int aligned_embed_dim, int num_heads, int aligned_head_dim, int intermediate_dim, int aligned_intermediate_dim, float eps, void *scratch)
void quantize_row_q8_k(const float *x, void *vy, int k)
void gemm_nt_q4_k_q8_k(const void *A_q8, const void *B, const float *bias, float *C, int M, int N, int K)
void ck_test_recurrent_split_qkv(const float *packed_qkv, float *q, float *k, float *v, int rows, int q_dim, int k_dim, int v_dim)
Split a packed recurrent QKV matrix into explicit Q, K, and V outputs.
void ck_test_vec_dot_q6_k_q8_k(const void *weight_q6_k, const void *input_q8_k, float *output, int cols)
void ck_test_gemv_q8_0_q8_0(const void *weight_q8_0, const float *input_f32, float *output, int rows, int cols)
Q8_0 x Q8_0 quantized GEMV - matches llama.cpp's approach.
void ck_test_vec_dot_q8_0_q8_0(const void *weight_q8_0, const void *input_q8_0, float *output, int cols)
Direct Q8_0 x Q8_0 dot product test (takes pre-quantized Q8_0 input)
void ck_test_swiglu(const float *gate_up, float *output, int n_tokens, int intermediate_dim)
SwiGLU activation.
void ck_test_gemm_q6_k(const void *weight_q6k, const float *input_f32, float *output, int rows, int cols, int n_tokens)
Test Q6_K x Q8_K GEMM (batch matrix multiply)
void ck_test_vec_dot_q5_0_q8_0(const void *weight_q5_0, const void *input_q8_0, float *output, int cols)
Direct Q5_0 x Q8_0 dot product test (takes pre-quantized Q8_0 input)
void gemv_q6_k_q8_k(float *y, const void *W, const void *x_q8, int M, int K)
GEMV: y = W @ x where W is Q6_K and x is Q8_K.
void ck_test_recurrent_norm_gate(const float *x, const float *gate, const float *weight, float *out, int rows, int num_heads, int head_dim, float eps)
Per-head RMSNorm followed by SiLU(z) gating for recurrent outputs.
void vec_dot_q5_0_q8_0(int n, float *s, const void *vx, const void *vy)
Auto-dispatch quantized dot product Q5_0 x Q8_0.
void vec_dot_q6_k_q8_k(int n, float *s, const void *vx, const void *vy)
Q6_K x Q8_K dot product (single row)
void recurrent_silu_forward(const float *x, float *out, int rows, int dim)
int ck_get_qk_k(void)
Get QK_K (elements per super-block)
void rmsnorm_forward(const float *input, const float *gamma, float *output, float *rstd_cache, int tokens, int d_model, int aligned_embed_dim, float eps)
void ck_test_gemm_q8_0(const void *weight_q8_0, const float *input_f32, float *output, int rows, int cols, int n_tokens)
Test Q8_0 x Q8_0 GEMM (batch matrix multiply)
void rope_precompute_cache(float *cos_cache, float *sin_cache, int max_seq_len, int head_dim, float base, int rotary_dim, const char *scaling_type, float scaling_factor)
void gemm_nt_q8_0_q8_0(const void *A_q8, const void *B_q8, const float *bias, float *C, int M, int N, int K)
gemm_nt_q8_0_q8_0 with optional bias (matches header signature)
void gated_deltanet_autoregressive_forward(const float *q, const float *k, const float *v, const float *g, const float *beta, const float *state_in, float *state_out, float *out, int num_heads, int state_dim, float norm_eps)
void rope_forward_qk(float *q, float *k, const float *cos_cache, const float *sin_cache, int num_heads, int num_kv_heads, int num_tokens, int head_dim, int aligned_head_dim, int pos_offset)
void gemv_q8_0_q8_0(float *y, const void *W, const void *x_q8, int M, int K)
Matrix-vector multiply with Q8_0 weights and Q8_0 input.
void gemm_nt_q5_0_q8_0(const void *A_q8, const void *B_q5, const float *bias, float *C, int M, int N, int K)
Batch GEMM with Q5_0 weights and Q8_0 activations for prefill.
void gemv_q4_k_q8_k(float *y, const void *W, const void *x_q8, int M, int K)
void ssm_conv1d_forward(const float *conv_x, const float *kernel, float *out, int kernel_size, int num_channels, int num_tokens, int num_seqs)
void ck_test_gemv_q5_0(const void *weight_q5_0, const float *input_f32, float *output, int rows, int cols)
Q5_0 GEMV - matrix-vector multiply with Q5_0 weights.
void gemm_nt_q6_k_q8_k(const void *A_q8, const void *B, const float *bias, float *C, int M, int N, int K)
NT GEMM: C = A @ B^T where A is Q8_K and B is Q6_K.
size_t mega_fused_outproj_mlp_prefill_scratch_size(int tokens, int aligned_embed_dim, int num_heads, int aligned_head_dim, int aligned_intermediate_dim)
Get scratch buffer size for mega_fused_outproj_mlp_prefill.
void ck_test_ssm_conv1d(const float *conv_x, const float *kernel, float *out, int kernel_size, int num_channels, int num_tokens, int num_seqs)
qwen3next/Qwen3.5 SSM causal depthwise convolution.
void ck_test_recurrent_qk_l2_norm(float *q, float *k, int rows, int q_dim, int k_dim, int head_dim, float eps)
Apply per-head L2 normalization to recurrent Q/K rows in-place.
void recurrent_split_qkv_forward(const float *packed_qkv, float *q, float *k, float *v, int rows, int q_dim, int k_dim, int v_dim)
void dequant_q6_k_row(const void *src, float *dst, size_t n_elements)
Dequantize Q6_K row (multiple blocks)
void quantize_row_q8_0(const float *x, void *vy, int k)
Quantize FP32 to Q8_0 format (scalar reference)
void ck_test_rope_interleaved(float *q, float *k, int n_tokens, int n_heads, int n_heads_kv, int head_dim, int pos_offset, float theta)
RoPE with interleaved format (for llama.cpp compatibility)
void split_q_gate_forward(const float *packed_qg, float *q, float *gate, int rows, int q_dim, int gate_dim, int group_dim)
int ck_get_block_q4_k_size(void)
Get Q4_K block size in bytes.
int ck_get_block_q6_k_size(void)
Get Q6_K block size in bytes.
void ck_test_gemv_q8_0(const void *weight_q8_0, const float *input_f32, float *output, int rows, int cols)
Q8_0 GEMV - matrix-vector multiply with Q8_0 weights.
void vec_dot_q8_0_q8_0(int n, float *s, const void *vx, const void *vy)
Auto-dispatch quantized dot product Q8_0 x Q8_0.
void dequant_q4_k_row(const void *src, float *dst, size_t n_elements)
Dequantize Q4_K row (multiple blocks)
void recurrent_norm_gate_forward(const float *x, const float *gate, const float *weight, float *out, int rows, int num_heads, int head_dim, float eps)
void recurrent_dt_gate_forward(const float *alpha, const float *dt_bias, const float *a, float *gate, int rows, int num_heads, int state_dim)
void ck_test_gemv_q6_k(const void *weight_q6k, const float *input_f32, float *output, int cols)
Q6_K GEMV.
void ck_test_vec_dot_q4_k_q8_k(const void *weight_q4_k, const void *input_q8_k, float *output, int cols)
void ck_test_outproj_mlp_fused_q5_0(const float *attn_out, const float *residual, const float *ln2_gamma, const void *wo, const void *w1, const void *w2, float *output, int tokens, int num_heads, int head_dim, int embed_dim, int intermediate, float eps, int w2_is_q6k)
Test mega-fused OutProj + MLP kernel (Q5_0 weights)
C-Kernel-Engine Parity Testing API.
Quantization block structures for weight-only quantization.