1use super::*;
6
7impl MoeLayer {
8 pub fn new(
9 weights: MoeWeights,
10 num_experts: usize,
11 gate_nvfp4: Option<QuantizedWeight>,
12 gpu: &dyn GpuBackend,
13 config: &atlas_core::config::ModelConfig,
14 ) -> Result<Self> {
15 Self::new_with_hash(weights, num_experts, gate_nvfp4, None, gpu, config)
16 }
17
18 #[allow(clippy::too_many_arguments)]
22 pub fn new_with_hash(
23 weights: MoeWeights,
24 num_experts: usize,
25 gate_nvfp4: Option<QuantizedWeight>,
26 tid2eid_dev: Option<DevicePtr>,
27 gpu: &dyn GpuBackend,
28 config: &atlas_core::config::ModelConfig,
29 ) -> Result<Self> {
30 anyhow::ensure!(
34 config.num_experts_per_tok <= num_experts && num_experts > 0,
35 "MoE config invalid: num_experts_per_tok={} must be in 1..={}",
36 config.num_experts_per_tok,
37 num_experts,
38 );
39 anyhow::ensure!(
44 config.num_experts_per_tok <= crate::layers::ops::MOE_TOPK_SIGMOID_MAX_TOP_K
45 && num_experts <= crate::layers::ops::MOE_TOPK_SIGMOID_MAX_EXPERTS,
46 "MoE config exceeds the routing kernels' fixed shared-memory bounds: \
47 num_experts_per_tok={} (max {}), num_experts={} (max {}). Raise \
48 MAX_TOP_K / MAX_EXPERTS in kernels/gb10/common/moe_topk_sigmoid.cu \
49 and their mirrors in layers::ops together.",
50 config.num_experts_per_tok,
51 crate::layers::ops::MOE_TOPK_SIGMOID_MAX_TOP_K,
52 num_experts,
53 crate::layers::ops::MOE_TOPK_SIGMOID_MAX_EXPERTS,
54 );
55 let gate_ptrs = build_ptr_table(&weights.experts, |e| &e.gate_proj, gpu)?;
56 let up_ptrs = build_ptr_table(&weights.experts, |e| &e.up_proj, gpu)?;
57 let down_ptrs = build_ptr_table(&weights.experts, |e| &e.down_proj, gpu)?;
58
59 let weights_correction_bias: Option<DevicePtr> =
64 weights.correction_bias.map(|dw| dw.weight);
65
66 let _ = num_experts;
67 let rms_norm_k = gpu.kernel("norm", "rms_norm")?;
68 Ok(Self {
69 weights,
70 experts_scale_kind: crate::weight_map::WeightQuantFormat::Nvfp4,
74 shared_experts_scale_kind: crate::weight_map::WeightQuantFormat::Nvfp4,
75 gate_nvfp4,
76 pre_expert_norm: None,
77 pre_expert_norm_k: rms_norm_k,
78 dense_gemv: gpu.kernel("gemv", "dense_gemv_bf16")?,
79 w4a16_gemv: gpu.kernel("w4a16_gemv", "w4a16_gemv")?,
80 w4a16_gemv_sw: super::super::try_kernel(gpu, "w4a16_gemv", "w4a16_gemv_sw"),
81 w4a16_gemm: gpu.kernel("w4a16", "w4a16_gemm")?,
82 dense_gemm: gpu.kernel("gemm", "dense_gemm_bf16")?,
83 dense_gemm_router: super::super::try_kernel(gpu, "gemm", "dense_gemm_bf16_router"),
84 dense_gemm_pipelined: super::super::try_kernel(
85 gpu,
86 "gemm",
87 "dense_gemm_bf16_pipelined",
88 ),
89 dense_gemm_f32out: super::super::try_kernel(gpu, "gemm", "dense_gemm_bf16_f32out"),
92 dense_gemm_f32in: super::super::try_kernel(gpu, "gemm", "dense_gemm_f32in_f32out"),
93 moe_topk_f32: super::super::try_kernel(gpu, "moe_topk", "moe_topk_softmax_f32"),
94 moe_expert_gate_up_shared: gpu
95 .kernel("moe_shared_expert_fused", "moe_expert_gate_up_shared")?,
96 moe_expert_silu_down_shared: gpu
97 .kernel("moe_shared_expert_fused", "moe_expert_silu_down_shared")?,
98 moe_topk: gpu.kernel("moe_topk", "moe_topk_softmax")?,
99 moe_weighted_sum_blend: gpu.kernel("moe_expert_gemv", "moe_weighted_sum_blend")?,
100 residual_add: gpu.kernel("residual_add", "bf16_residual_add")?,
101 moe_topk_batched: gpu.kernel("moe_topk", "moe_topk_softmax_batched")?,
102 moe_expert_gate_up_shared_batch2: gpu
103 .kernel("moe_fused_batch2", "moe_expert_gate_up_shared_batch2")?,
104 moe_expert_silu_down_shared_batch2: gpu
105 .kernel("moe_fused_batch2", "moe_expert_silu_down_shared_batch2")?,
106 moe_weighted_sum_blend_batch2: gpu
107 .kernel("moe_fused_batch2", "moe_weighted_sum_blend_batch2")?,
108 w4a16_gemv_batch2: gpu.kernel("w4a16_gemv", "w4a16_gemv_batch2")?,
109 moe_expert_gate_up_shared_batch3: gpu
110 .kernel("moe_fused_batch3", "moe_expert_gate_up_shared_batch3")?,
111 moe_expert_silu_down_shared_batch3: gpu
112 .kernel("moe_fused_batch3", "moe_expert_silu_down_shared_batch3")?,
113 moe_weighted_sum_blend_batch3: gpu
114 .kernel("moe_fused_batch3", "moe_weighted_sum_blend_batch3")?,
115 w4a16_gemv_batch3: gpu.kernel("w4a16_gemv", "w4a16_gemv_batch3")?,
116 moe_expert_gate_up_shared_token_major: gpu
117 .kernel("moe_prefill", "moe_expert_gate_up_shared_prefill")?,
118 moe_expert_silu_down_shared_token_major: gpu
119 .kernel("moe_prefill", "moe_expert_silu_down_shared_prefill")?,
120 moe_weighted_sum_blend_token_major: gpu
121 .kernel("moe_prefill", "moe_weighted_sum_blend_prefill")?,
122 moe_decode_atomic_c4_silu_down_accum_k: super::super::try_kernel(
123 gpu,
124 "moe_decode_atomic_c4",
125 "moe_decode_atomic_c4_silu_down_accum",
126 ),
127 moe_decode_atomic_c4_finalize_k: super::super::try_kernel(
128 gpu,
129 "moe_decode_atomic_c4",
130 "moe_decode_atomic_c4_finalize",
131 ),
132 moe_sort_by_expert: gpu.kernel("moe", "moe_sort_by_expert")?,
133 moe_sorted_gate_up: gpu.kernel("moe_sorted", "moe_sorted_gate_up")?,
134 moe_sorted_silu_down: gpu.kernel("moe_sorted", "moe_sorted_silu_down")?,
135 moe_grouped_gemm: gpu.kernel("moe_w4a16", "moe_w4a16_grouped_gemm_ptrtable")?,
136 moe_grouped_gemm_k32: if std::env::var("ATLAS_MOE_GROUPED_K32").as_deref() == Ok("1") {
137 super::super::try_kernel(gpu, "moe_w4a16", "moe_w4a16_grouped_gemm_ptrtable_k32")
138 } else {
139 KernelHandle(0)
140 },
141 moe_grouped_gemm_m256: if std::env::var("ATLAS_MOE_GROUPED_M256").as_deref() == Ok("1")
142 {
143 super::super::try_kernel(gpu, "moe_w4a16", "moe_w4a16_grouped_gemm_ptrtable_m256")
144 } else {
145 KernelHandle(0)
146 },
147 moe_grouped_gemm_t: gpu.kernel("moe_w4a16", "moe_w4a16_grouped_gemm_ptrtable_t")?,
148 moe_grouped_gemm_t_k64: gpu
149 .kernel("moe_w4a16", "moe_w4a16_grouped_gemm_ptrtable_t_k64")?,
150 moe_fused_gate_up_t: gpu.kernel("moe_w4a16", "moe_w4a16_fused_gate_up_t")?,
151 moe_fused_gate_up_t_k64: gpu.kernel("moe_w4a16", "moe_w4a16_fused_gate_up_t_k64")?,
152 moe_grouped_gemm_e8m0: super::super::try_kernel(
155 gpu,
156 "moe_w4a16",
157 "moe_w4a16_grouped_gemm_ptrtable_e8m0",
158 ),
159 moe_grouped_gemm_t_e8m0: super::super::try_kernel(
160 gpu,
161 "moe_w4a16",
162 "moe_w4a16_grouped_gemm_ptrtable_t_e8m0",
163 ),
164 moe_grouped_gemm_t_k64_e8m0: super::super::try_kernel(
165 gpu,
166 "moe_w4a16",
167 "moe_w4a16_grouped_gemm_ptrtable_t_k64_e8m0",
168 ),
169 moe_fused_gate_up_t_e8m0: super::super::try_kernel(
170 gpu,
171 "moe_w4a16",
172 "moe_w4a16_fused_gate_up_t_e8m0",
173 ),
174 moe_fused_gate_up_t_k64_e8m0: super::super::try_kernel(
175 gpu,
176 "moe_w4a16",
177 "moe_w4a16_fused_gate_up_t_k64_e8m0",
178 ),
179 moe_fused_gate_up_t_k64_m128: super::super::try_kernel(
183 gpu,
184 "moe_w4a16",
185 "moe_w4a16_fused_gate_up_t_k64_m128",
186 ),
187 moe_fused_gate_up_t_k64_fp4: super::super::try_kernel(
191 gpu,
192 "moe_w4a16",
193 "moe_w4a16_fused_gate_up_t_k64_fp4",
194 ),
195 moe_fp8_grouped_gemm_t: gpu.kernel("moe_w4a16", "moe_fp8_grouped_gemm_ptrtable_t")?,
196 moe_fp8_grouped_gemm_k: super::super::try_kernel(
200 gpu,
201 "moe_fp8_grouped_gemm",
202 "moe_fp8_grouped_gemm",
203 ),
204 moe_build_tile_worklist_k: super::super::try_kernel(
207 gpu,
208 "moe",
209 "moe_build_tile_worklist",
210 ),
211 moe_w8a8_grouped_gemm_k: super::super::try_kernel(
212 gpu,
213 "moe_w8a8_grouped_gemm",
214 "moe_w8a8_grouped_gemm",
215 ),
216 moe_w8a8_grouped_gemm_pm4_k: super::super::try_kernel(
219 gpu,
220 "moe_w8a8_grouped_gemm",
221 "moe_w8a8_grouped_gemm_pm4",
222 ),
223 per_token_group_quant_fp8_k: ops::Fp8ActQuant::resolve(gpu),
224 silu_mul_quant_fp8_k: super::super::try_kernel(
228 gpu,
229 "moe_silu_mul",
230 "silu_mul_quant_fp8",
231 ),
232 fp8_gemm_t_blockscaled_k: super::super::try_kernel(
233 gpu,
234 "fp8_gemm_t_blockscaled",
235 "fp8_gemm_t_blockscaled",
236 ),
237 moe_bf16_grouped_gemm_k: super::super::try_kernel(
238 gpu,
239 "moe_bf16_grouped_gemm",
240 "moe_bf16_grouped_gemm",
241 ),
242 moe_expert_gate_up_shared_bf16_k: super::super::try_kernel(
243 gpu,
244 "moe_shared_expert_fused_bf16",
245 "moe_expert_gate_up_shared_bf16",
246 ),
247 moe_expert_silu_down_shared_bf16_k: super::super::try_kernel(
248 gpu,
249 "moe_shared_expert_fused_bf16",
250 "moe_expert_silu_down_shared_bf16",
251 ),
252 moe_expert_gate_up_shared_bf16_batch2_k: super::super::try_kernel(
253 gpu,
254 "moe_shared_expert_fused_bf16_batch2",
255 "moe_expert_gate_up_shared_bf16_batch2",
256 ),
257 moe_expert_silu_down_shared_bf16_batch2_k: super::super::try_kernel(
258 gpu,
259 "moe_shared_expert_fused_bf16_batch2",
260 "moe_expert_silu_down_shared_bf16_batch2",
261 ),
262 w8a16_gemm_k: super::super::try_kernel(gpu, "w8a16_gemm", "w8a16_gemm"),
263 w8a16_gemm_pipelined_k: super::super::try_kernel(
264 gpu,
265 "w8a16_gemm_pipelined",
266 "w8a16_gemm_pipelined",
267 ),
268 moe_gate_topk_fused_k: super::super::try_kernel(
269 gpu,
270 "moe_gate_topk",
271 "moe_gate_topk_fused",
272 ),
273 w4a16_gemm_t: gpu.kernel("w4a16", "w4a16_gemm_t")?,
274 bf16_to_fp8_k: gpu.kernel("w4a16", "bf16_to_fp8")?,
275 fp8_gemm_k: gpu.kernel("w4a16", "fp8_gemm_t")?,
276 moe_silu_mul: gpu.kernel("moe_silu_mul", "moe_silu_mul")?,
277 moe_act_mul: gpu.kernel("moe_silu_mul", "moe_silu_mul")?, gelu_activation: false,
279 moe_unpermute_reduce: gpu.kernel("moe", "moe_unpermute_reduce_indexed")?,
280 moe_batched_blend: gpu.kernel("moe", "moe_batched_blend")?,
281 gate_ptrs,
282 up_ptrs,
283 down_ptrs,
284 gate_ptrs_t: None,
285 up_ptrs_t: None,
286 down_ptrs_t: None,
287 cutlass_grouped_host: None,
288 _cutlass_sfb_owned: Vec::new(),
289 down_t_scratch_packed: None,
290 down_t_scratch_scale: None,
291 moe_transpose_u8_batched_k: gpu
292 .kernel("moe_transpose_batched", "moe_transpose_u8_batched")?,
293 moe_expert_gate_up_shared_t_k: gpu
296 .kernel("moe_shared_expert_fused_t", "moe_expert_gate_up_shared_t")?,
297 moe_expert_silu_down_shared_t_k: gpu
298 .kernel("moe_shared_expert_fused_t", "moe_expert_silu_down_shared_t")?,
299 moe_expert_gate_up_shared_t_e8m0_k: super::super::try_kernel(
303 gpu,
304 "moe_shared_expert_fused_t",
305 "moe_expert_gate_up_shared_t_e8m0",
306 ),
307 moe_expert_silu_down_shared_t_e8m0_k: super::super::try_kernel(
308 gpu,
309 "moe_shared_expert_fused_t",
310 "moe_expert_silu_down_shared_t_e8m0",
311 ),
312 moe_topk_sqrtsoftplus_k: super::super::try_kernel(
315 gpu,
316 "moe_topk_sqrt",
317 "moe_topk_sqrtsoftplus",
318 ),
319 moe_topk_sqrtsoftplus_batched_k: super::super::try_kernel(
320 gpu,
321 "moe_topk_sqrt",
322 "moe_topk_sqrtsoftplus_batched",
323 ),
324 router_logits_n: (config.num_experts + config.zero_expert_num) as u32,
328 moe_topk_softmax_bias_k: super::super::try_kernel(
329 gpu,
330 "moe_topk_softmax_bias",
331 "moe_topk_softmax_bias",
332 ),
333 moe_topk_softmax_bias_batched_k: super::super::try_kernel(
334 gpu,
335 "moe_topk_softmax_bias",
336 "moe_topk_softmax_bias_batched",
337 ),
338 moe_zero_expert_add_k: super::super::try_kernel(
339 gpu,
340 "moe_topk_softmax_bias",
341 "moe_zero_expert_add",
342 ),
343 zero_accum_dev: gpu.alloc(16384 * 4)?,
346 moe_hash_route_k: super::super::try_kernel(gpu, "moe_hash_route", "moe_hash_route"),
347 moe_hash_route_batched_k: super::super::try_kernel(
348 gpu,
349 "moe_hash_route",
350 "moe_hash_route_batched",
351 ),
352 tid2eid_dev,
353 moe_expert_gate_up_shared_batch2_t_k: gpu.kernel(
354 "moe_shared_expert_fused_batch2_t",
355 "moe_expert_gate_up_shared_batch2_t",
356 )?,
357 moe_expert_silu_down_shared_batch2_t_k: gpu.kernel(
358 "moe_shared_expert_fused_batch2_t",
359 "moe_expert_silu_down_shared_batch2_t",
360 )?,
361 moe_expert_gate_up_shared_batch3_t_k: gpu.kernel(
362 "moe_shared_expert_fused_batch3_t",
363 "moe_expert_gate_up_shared_batch3_t",
364 )?,
365 moe_expert_silu_down_shared_batch3_t_k: gpu.kernel(
366 "moe_shared_expert_fused_batch3_t",
367 "moe_expert_silu_down_shared_batch3_t",
368 )?,
369 moe_expert_gate_up_shared_fp8_t_k: gpu.kernel(
370 "moe_shared_expert_fused_fp8_t",
371 "moe_expert_gate_up_shared_fp8_t",
372 )?,
373 moe_expert_silu_down_shared_fp8_t_k: gpu.kernel(
374 "moe_shared_expert_fused_fp8_t",
375 "moe_expert_silu_down_shared_fp8_t",
376 )?,
377 moe_expert_gate_up_shared_fp8_batch2_t_k: gpu.kernel(
378 "moe_shared_expert_fused_fp8_batch2_t",
379 "moe_expert_gate_up_shared_fp8_batch2_t",
380 )?,
381 moe_expert_silu_down_shared_fp8_batch2_t_k: gpu.kernel(
382 "moe_shared_expert_fused_fp8_batch2_t",
383 "moe_expert_silu_down_shared_fp8_batch2_t",
384 )?,
385 moe_expert_gate_up_shared_fp8_batch3_t_k: gpu.kernel(
386 "moe_shared_expert_fused_fp8_batch3_t",
387 "moe_expert_gate_up_shared_fp8_batch3_t",
388 )?,
389 moe_expert_silu_down_shared_fp8_batch3_t_k: gpu.kernel(
390 "moe_shared_expert_fused_fp8_batch3_t",
391 "moe_expert_silu_down_shared_fp8_batch3_t",
392 )?,
393 unified_layout: std::env::var("ATLAS_UNIFIED_MOE_LAYOUT")
394 .map(|v| v == "1" || v.eq_ignore_ascii_case("true"))
395 .unwrap_or(false),
396 hybrid_layout: std::env::var("ATLAS_HYBRID_MOE_LAYOUT")
397 .map(|v| v == "1" || v.eq_ignore_ascii_case("true"))
398 .unwrap_or(false),
399 nvfp4_gate_up_m128: std::env::var("ATLAS_NVFP4_GATE_UP_M128")
400 .map(|v| v == "1" || v.eq_ignore_ascii_case("true"))
401 .unwrap_or(false),
402 gateup_fp4: std::env::var("ATLAS_HOLO_MOE_GATEUP_FP4")
404 .map(|v| v == "1" || v.eq_ignore_ascii_case("true"))
405 .unwrap_or(false),
406 down_fp4: std::env::var("ATLAS_HOLO_MOE_DOWN_FP4")
407 .map(|v| v == "1" || v.eq_ignore_ascii_case("true"))
408 .unwrap_or(false),
409 shared_gate_t: None,
410 shared_up_t: None,
411 shared_down_t: None,
412 gate_fp8: None,
413 shared_gate_fp8: None,
414 shared_up_fp8: None,
415 shared_down_fp8: None,
416 prefill_stream: gpu.create_stream()?,
417 event_a: gpu.create_event()?,
418 event_b: gpu.create_event()?,
419 moe_expert_gate_up_shared_fp8: gpu.kernel(
420 "moe_shared_expert_fused_fp8",
421 "moe_expert_gate_up_shared_fp8",
422 )?,
423 moe_expert_silu_down_shared_fp8: gpu.kernel(
424 "moe_shared_expert_fused_fp8",
425 "moe_expert_silu_down_shared_fp8",
426 )?,
427 moe_expert_gate_up_shared_fp8_batch2: gpu.kernel(
429 "moe_shared_expert_fused_fp8_batch2",
430 "moe_expert_gate_up_shared_fp8_batch2",
431 )?,
432 moe_expert_silu_down_shared_fp8_batch2: gpu.kernel(
433 "moe_shared_expert_fused_fp8_batch2",
434 "moe_expert_silu_down_shared_fp8_batch2",
435 )?,
436 moe_weighted_sum_blend_fp8_batch2: gpu.kernel(
437 "moe_shared_expert_fused_fp8_batch2",
438 "moe_weighted_sum_blend_fp8_batch2",
439 )?,
440 moe_expert_gate_up_shared_fp8_batch3: gpu.kernel(
441 "moe_shared_expert_fused_fp8_batch3",
442 "moe_expert_gate_up_shared_fp8_batch3",
443 )?,
444 moe_expert_silu_down_shared_fp8_batch3: gpu.kernel(
445 "moe_shared_expert_fused_fp8_batch3",
446 "moe_expert_silu_down_shared_fp8_batch3",
447 )?,
448 moe_weighted_sum_blend_fp8_batch3: gpu.kernel(
449 "moe_shared_expert_fused_fp8_batch3",
450 "moe_weighted_sum_blend_fp8_batch3",
451 )?,
452 fp8_gate_weight_ptrs: None,
453 fp8_up_weight_ptrs: None,
454 fp8_down_weight_ptrs: None,
455 bf16_gate_weight_ptrs: None,
456 bf16_up_weight_ptrs: None,
457 bf16_down_weight_ptrs: None,
458 bf16_shared_expert: None,
459 fp8_shared_expert: None,
460 moe_down_t_k64_fp4: super::super::try_kernel(
461 gpu,
462 "moe_w4a16",
463 "moe_w4a16_down_t_k64_fp4",
464 ),
465 moe_permute_tokens_k: super::super::try_kernel(gpu, "moe", "moe_permute_tokens"),
466 is_dflash_capture_layer: false,
468 lora: None,
469 correction_bias_dev: weights_correction_bias,
470 moe_topk_sigmoid_k: super::super::try_kernel(gpu, "moe_topk_sig", "moe_topk_sigmoid"),
480 moe_topk_sigmoid_batched_k: super::super::try_kernel(
481 gpu,
482 "moe_topk_sig",
483 "moe_topk_sigmoid_batched",
484 ),
485 })
486 }
487}