char-fork/llama.cpp
git clone https://git.t4t.associates/char-fork/llama.cpp
d4abd573f
char/aliceai-t5-moe
1#include "common.cuh" 2#include "mmq.cuh" 3#include "quantize.cuh" 4#include "mmid.cuh" 5 6#include <cstdint> 7 8static void ggml_cuda_mul_mat_q_switch_type(ggml_backend_cuda_context & ctx, const mmq_args & args, cudaStream_t stream) { 9 switch (args.type_x) { 10 case GGML_TYPE_Q1_0: 11 mul_mat_q_case<GGML_TYPE_Q1_0>(ctx, args, stream); 12 break; 13 case GGML_TYPE_Q2_0: 14 mul_mat_q_case<GGML_TYPE_Q2_0>(ctx, args, stream); 15 break; 16 case GGML_TYPE_Q4_0: 17 mul_mat_q_case<GGML_TYPE_Q4_0>(ctx, args, stream); 18 break; 19 case GGML_TYPE_Q4_1: 20 mul_mat_q_case<GGML_TYPE_Q4_1>(ctx, args, stream); 21 break; 22 case GGML_TYPE_Q5_0: 23 mul_mat_q_case<GGML_TYPE_Q5_0>(ctx, args, stream); 24 break; 25 case GGML_TYPE_Q5_1: 26 mul_mat_q_case<GGML_TYPE_Q5_1>(ctx, args, stream); 27 break; 28 case GGML_TYPE_Q8_0: 29 mul_mat_q_case<GGML_TYPE_Q8_0>(ctx, args, stream); 30 break; 31// ----------------------------------------------------------------------- 32 case GGML_TYPE_Q2_K: 33 mul_mat_q_case<GGML_TYPE_Q2_K>(ctx, args, stream); 34 break; 35 case GGML_TYPE_Q3_K: 36 mul_mat_q_case<GGML_TYPE_Q3_K>(ctx, args, stream); 37 break; 38 case GGML_TYPE_Q4_K: 39 mul_mat_q_case<GGML_TYPE_Q4_K>(ctx, args, stream); 40 break; 41 case GGML_TYPE_Q5_K: 42 mul_mat_q_case<GGML_TYPE_Q5_K>(ctx, args, stream); 43 break; 44 case GGML_TYPE_Q6_K: 45 mul_mat_q_case<GGML_TYPE_Q6_K>(ctx, args, stream); 46 break; 47// ----------------------------------------------------------------------- 48 case GGML_TYPE_IQ1_S: 49 mul_mat_q_case<GGML_TYPE_IQ1_S>(ctx, args, stream); 50 break; 51 case GGML_TYPE_IQ2_XXS: 52 mul_mat_q_case<GGML_TYPE_IQ2_XXS>(ctx, args, stream); 53 break; 54 case GGML_TYPE_IQ2_XS: 55 mul_mat_q_case<GGML_TYPE_IQ2_XS>(ctx, args, stream); 56 break; 57 case GGML_TYPE_IQ2_S: 58 mul_mat_q_case<GGML_TYPE_IQ2_S>(ctx, args, stream); 59 break; 60 case GGML_TYPE_IQ3_XXS: 61 mul_mat_q_case<GGML_TYPE_IQ3_XXS>(ctx, args, stream); 62 break; 63 case GGML_TYPE_IQ3_S: 64 mul_mat_q_case<GGML_TYPE_IQ3_S>(ctx, args, stream); 65 break; 66 case GGML_TYPE_IQ4_XS: 67 mul_mat_q_case<GGML_TYPE_IQ4_XS>(ctx, args, stream); 68 break; 69 case GGML_TYPE_IQ4_NL: 70 mul_mat_q_case<GGML_TYPE_IQ4_NL>(ctx, args, stream); 71 break; 72// ----------------------------------------------------------------------- 73 case GGML_TYPE_MXFP4: 74 mul_mat_q_case<GGML_TYPE_MXFP4>(ctx, args, stream); 75 break; 76 case GGML_TYPE_NVFP4: 77 mul_mat_q_case<GGML_TYPE_NVFP4>(ctx, args, stream); 78 break; 79 default: 80 GGML_ABORT("fatal error"); 81 break; 82 } 83} 84 85void ggml_cuda_mul_mat_q( 86 ggml_backend_cuda_context & ctx, const ggml_tensor * src0, const ggml_tensor * src1, const ggml_tensor * ids, ggml_tensor * dst) { 87 GGML_ASSERT( src1->type == GGML_TYPE_F32); 88 GGML_ASSERT( dst->type == GGML_TYPE_F32); 89 GGML_ASSERT(!ids || ids->type == GGML_TYPE_I32); // Optional, used for batched GGML_MUL_MAT_ID. 90 91 GGML_TENSOR_BINARY_OP_LOCALS; 92 93 cudaStream_t stream = ctx.stream(); 94 const int cc = ggml_cuda_info().devices[ggml_cuda_get_device()].cc; 95 96 const size_t ts_src0 = ggml_type_size(src0->type); 97 const size_t ts_src1 = ggml_type_size(src1->type); 98 const size_t ts_dst = ggml_type_size(dst->type); 99 100 GGML_ASSERT( nb00 == ts_src0); 101 GGML_ASSERT( nb10 == ts_src1); 102 GGML_ASSERT( nb0 == ts_dst); 103 GGML_ASSERT(!ids || ids->nb[0] == ggml_type_size(ids->type)); 104 105 const char * src0_d = (const char *) src0->data; 106 const float * src1_d = (const float *) src1->data; 107 float * dst_d = (float *) dst->data; 108 109 // If src0 is a temporary compute buffer, clear any potential padding. 110 if (ggml_backend_buffer_get_usage(src0->buffer) == GGML_BACKEND_BUFFER_USAGE_COMPUTE) { 111 const size_t size_data = ggml_nbytes(src0); 112 const size_t size_alloc = ggml_backend_buffer_get_alloc_size(src0->buffer, src0); 113 if (size_alloc > size_data) { 114 GGML_ASSERT(ggml_is_contiguously_allocated(src0)); 115 GGML_ASSERT(!src0->view_src); 116 CUDA_CHECK(cudaMemsetAsync((char *) src0->data + size_data, 0, size_alloc - size_data, stream)); 117 } 118 } 119 120 const int64_t ne10_padded = GGML_PAD(ne10, MATRIX_ROW_PADDING); 121 122 const int64_t s01 = src0->nb[1] / ts_src0; 123 const int64_t s1 = dst->nb[1] / ts_dst; 124 const int64_t s02 = src0->nb[2] / ts_src0; 125 const int64_t s2 = dst->nb[2] / ts_dst; 126 const int64_t s03 = src0->nb[3] / ts_src0; 127 const int64_t s3 = dst->nb[3] / ts_dst; 128 129 const bool fallback = ne01 % 128 != 0; 130 131 const bool use_native_fp4 = blackwell_mma_available(cc) && (src0->type == GGML_TYPE_MXFP4 || src0->type == GGML_TYPE_NVFP4); 132 const size_t y_block_size = use_native_fp4 ? sizeof(block_fp4_mmq) : sizeof(block_q8_1_mmq); 133 const size_t y_values_per_block = use_native_fp4 ? QK_FP4_MMQ : QK8_1_MMQ; 134 135 if (!ids) { 136 const size_t nbytes_src1_q8_1 = ne13*ne12 * ne11*ne10_padded * y_block_size/y_values_per_block + 137 ggml_cuda_mmq_get_J_max(src0->type, fallback, cc, ne11) * sizeof(block_q8_1_mmq); 138 ggml_cuda_pool_alloc<char> src1_q8_1(ctx.pool(), nbytes_src1_q8_1); 139 ggml_cuda_pool_alloc<float> src1_scale(ctx.pool()); 140 if (src0->type == GGML_TYPE_NVFP4 && use_native_fp4) { 141 src1_scale.alloc(ne13*ne12*ne11); 142 } 143 144 { 145 const int64_t s11 = src1->nb[1] / ts_src1; 146 const int64_t s12 = src1->nb[2] / ts_src1; 147 const int64_t s13 = src1->nb[3] / ts_src1; 148 if (use_native_fp4) { 149 static constexpr size_t align_float8 = 32; 150 const bool use_aligned_float8 = ggml_cuda_is_aligned(src1, align_float8); 151 static_assert(sizeof(block_fp4_mmq) == 4 * sizeof(block_q8_1)); 152 quantize_mmq_fp4_cuda(src1_d, nullptr, src1_q8_1.get(), src1_scale.ptr, src0->type, use_aligned_float8, ne10, s11, s12, s13, ne10_padded, 153 ne11, ne12, ne13, stream); 154 155 } else { 156 quantize_mmq_q8_1_cuda(src1_d, nullptr, src1_q8_1.get(), src0->type, ne10, s11, s12, s13, ne10_padded, 157 ne11, ne12, ne13, stream); 158 } 159 CUDA_CHECK(cudaGetLastError()); 160 } 161 162 // Stride depends on quantization format 163 const int64_t s12 = use_native_fp4 ? 164 ne11 * ne10_padded * sizeof(block_fp4_mmq) / (QK_FP4_MMQ * sizeof(int)) : 165 ne11 * ne10_padded * sizeof(block_q8_1) / (QK8_1 * sizeof(int)); 166 const int64_t s13 = ne12*s12; 167 168 const mmq_args args = { 169 src0_d, src0->type, (const int *) src1_q8_1.ptr, nullptr, nullptr, dst_d, 170 src0->type == GGML_TYPE_NVFP4 && use_native_fp4 ? src1_scale.ptr : nullptr, 171 ne00, ne01, ne1, s01, ne11, s1, 172 ne02, ne12, s02, s12, s2, 173 ne03, ne13, s03, s13, s3, 174 ne1, ne1}; 175 ggml_cuda_mul_mat_q_switch_type(ctx, args, stream); 176 return; 177 } 178 179 GGML_ASSERT(ne13 == 1); 180 GGML_ASSERT(nb12 % nb11 == 0); 181 GGML_ASSERT(nb2 % nb1 == 0); 182 183 const int64_t n_expert_used = ids->ne[0]; 184 const int64_t ne_get_rows = ne12 * n_expert_used; 185 GGML_ASSERT(ne1 == n_expert_used); 186 187 ggml_cuda_pool_alloc<int32_t> ids_src1(ctx.pool(), ne_get_rows); 188 ggml_cuda_pool_alloc<int32_t> ids_dst(ctx.pool(), ne_get_rows); 189 ggml_cuda_pool_alloc<int32_t> expert_bounds(ctx.pool(), ne02 + 1); 190 191 // gate/up activations are broadcast across experts (ne11 == 1): quantize each token once and 192 // scatter to its slots. ids_src1 then holds the inverse map (token slot -> compact row). 193 const bool dedup_bcast = ne11 == 1 && n_expert_used > 1; 194 195 { 196 GGML_ASSERT(ids->nb[0] == ggml_element_size(ids)); 197 const int si1 = ids->nb[1] / ggml_element_size(ids); 198 const int sis1 = nb12 / nb11; 199 200 ggml_cuda_launch_mm_ids_helper((const int32_t *) ids->data, ids_src1.get(), ids_dst.get(), expert_bounds.get(), 201 ne02, ne12, n_expert_used, ne11, si1, sis1, /*write_inverse =*/ dedup_bcast, stream); 202 CUDA_CHECK(cudaGetLastError()); 203 } 204 205 const size_t nbytes_src1_q8_1 = ne12*n_expert_used*ne10_padded * y_block_size/y_values_per_block + 206 ggml_cuda_mmq_get_J_max(src0->type, fallback, cc, ne11) * sizeof(block_q8_1_mmq); 207 ggml_cuda_pool_alloc<char> src1_q8_1(ctx.pool(), nbytes_src1_q8_1); 208 ggml_cuda_pool_alloc<float> src1_scale(ctx.pool()); 209 if (src0->type == GGML_TYPE_NVFP4 && use_native_fp4) { 210 src1_scale.alloc(ne12*n_expert_used); 211 } 212 213 const int64_t ne11_flat = ne12*n_expert_used; 214 const int64_t ne12_flat = 1; 215 const int64_t ne13_flat = 1; 216 217 { 218 const int64_t s11 = src1->nb[1] / ts_src1; 219 const int64_t s12 = src1->nb[2] / ts_src1; 220 const int64_t s13 = src1->nb[3] / ts_src1; 221 222 if (use_native_fp4) { 223 static constexpr size_t align_float8 = 32; 224 const bool use_aligned_float8 = ggml_cuda_is_aligned(src1, align_float8); 225 if (dedup_bcast) { 226 quantize_scatter_mmq_fp4_cuda(src1_d, ids_src1.get(), src1_q8_1.get(), src1_scale.ptr, src0->type, use_aligned_float8, ne10, 227 /*stride_token=*/s12, ne10_padded, ne12, ne11_flat, n_expert_used, stream); 228 } else { 229 quantize_mmq_fp4_cuda(src1_d, ids_src1.get(), src1_q8_1.get(), src1_scale.ptr, src0->type, use_aligned_float8, ne10, s11, s12, s13, 230 ne10_padded, ne11_flat, ne12_flat, ne13_flat, stream); 231 } 232 } else if (dedup_bcast) { 233 quantize_scatter_mmq_q8_1_cuda(src1_d, ids_src1.get(), src1_q8_1.get(), src0->type, ne10, 234 /*stride_token=*/s12, ne10_padded, ne12, ne11_flat, n_expert_used, stream); 235 } else { 236 quantize_mmq_q8_1_cuda(src1_d, ids_src1.get(), src1_q8_1.get(), src0->type, ne10, s11, s12, s13, 237 ne10_padded, ne11_flat, ne12_flat, ne13_flat, stream); 238 } 239 CUDA_CHECK(cudaGetLastError()); 240 } 241 242 static_assert(QK_FP4_MMQ == 8 * QK_MXFP4, "QK_FP4_MMQ needs to be 8 * QK_MXFP4"); 243 const int64_t s12 = use_native_fp4 ? ne11 * ne10_padded * sizeof(block_fp4_mmq) / (QK_FP4_MMQ * sizeof(int)) : 244 ne11 * ne10_padded * sizeof(block_q8_1) / (QK8_1 * sizeof(int)); 245 const int64_t s13 = ne12*s12; 246 247 // Each expert only sees ne12*n_expert_used/ne02 tokens on average. 248 // On RDNA3 and RDNA4 it is faster to pick the tile size against this value instead of ne12. 249 int64_t ncols_opt = ne12; 250 if (GGML_CUDA_CC_IS_RDNA3_0(cc) || GGML_CUDA_CC_IS_RDNA4(cc)) { 251 ncols_opt = (ne12*n_expert_used + ne02 - 1) / ne02; 252 } 253 254 // Note that ne02 is used instead of ne12 because the number of y channels determines the z dimension of the CUDA grid. 255 const mmq_args args = { 256 src0_d, src0->type, (const int *) src1_q8_1.get(), ids_dst.get(), expert_bounds.get(), dst_d, 257 src1_scale.ptr, 258 ne00, ne01, ne_get_rows, s01, ne_get_rows, s1, 259 ne02, ne02, s02, s12, s2, 260 ne03, ne13, s03, s13, s3, 261 ne12, ncols_opt}; 262 263 ggml_cuda_mul_mat_q_switch_type(ctx, args, stream); 264} 265 266bool ggml_cuda_should_use_mmq(enum ggml_type type, int cc, int64_t ne11, int64_t n_experts) { 267#ifdef GGML_CUDA_FORCE_CUBLAS 268 return false; 269#endif // GGML_CUDA_FORCE_CUBLAS 270 271 bool mmq_supported; 272 273 switch (type) { 274 case GGML_TYPE_Q1_0: 275 case GGML_TYPE_Q2_0: 276 case GGML_TYPE_Q4_0: 277 case GGML_TYPE_Q4_1: 278 case GGML_TYPE_Q5_0: 279 case GGML_TYPE_Q5_1: 280 case GGML_TYPE_Q8_0: 281// ------------------------------------------------- 282 case GGML_TYPE_Q2_K: 283 case GGML_TYPE_Q3_K: 284 case GGML_TYPE_Q4_K: 285 case GGML_TYPE_Q5_K: 286 case GGML_TYPE_Q6_K: 287// ------------------------------------------------- 288 case GGML_TYPE_IQ1_S: 289 case GGML_TYPE_IQ2_XXS: 290 case GGML_TYPE_IQ2_XS: 291 case GGML_TYPE_IQ2_S: 292 case GGML_TYPE_IQ3_XXS: 293 case GGML_TYPE_IQ3_S: 294 case GGML_TYPE_IQ4_XS: 295 case GGML_TYPE_IQ4_NL: 296// ------------------------------------------------- 297 case GGML_TYPE_MXFP4: 298 case GGML_TYPE_NVFP4: 299 mmq_supported = true; 300 break; 301 default: 302 mmq_supported = false; 303 break; 304 } 305 306 if (!mmq_supported) { 307 return false; 308 } 309 310 // MMQ tiles require at least 48 KiB per-block shared memory; fall back to BLAS otherwise. 311 { 312 const int id = ggml_cuda_get_device(); 313 const size_t smpbo = ggml_cuda_info().devices[id].smpbo; 314 if (smpbo < 48 * 1024) { 315 return false; 316 } 317 } 318 319 if (turing_mma_available(cc)) { 320 return true; 321 } 322 323 if (ggml_cuda_highest_compiled_arch(cc) < GGML_CUDA_CC_DP4A) { 324 // for MoE, mmq is faster even without native dp4a 325 // TODO: check if cards older than pascal might benefit from this as well 326 return cc >= GGML_CUDA_CC_PASCAL && n_experts > 0; 327 } 328 329#ifdef GGML_CUDA_FORCE_MMQ 330 return true; 331#endif //GGML_CUDA_FORCE_MMQ 332 333 if (GGML_CUDA_CC_IS_NVIDIA(cc)) { 334 return !fp16_mma_hardware_available(cc) || ne11 < MMQ_DP4A_MAX_BATCH_SIZE; 335 } 336 337 if (amd_mfma_available(cc)) { 338 // As of ROCM 7.0 rocblas/tensile performs very poorly on CDNA3 and hipblaslt (via ROCBLAS_USE_HIPBLASLT) 339 // performs better but is currently suffering from a crash on this architecture. 340 // TODO: Revisit when hipblaslt is fixed on CDNA3 341 if (GGML_CUDA_CC_IS_CDNA3(cc)) { 342 return true; 343 } 344 if (n_experts > 64 || ne11 <= 128) { 345 return true; 346 } 347 if (type == GGML_TYPE_Q4_0 || type == GGML_TYPE_Q4_1 || type == GGML_TYPE_Q5_0 || type == GGML_TYPE_Q5_1) { 348 return true; 349 } 350 if (ne11 <= 256 && (type == GGML_TYPE_Q4_K || type == GGML_TYPE_Q5_K)) { 351 return true; 352 } 353 return false; 354 } 355 356 if (amd_wmma_available(cc)) { 357 if (GGML_CUDA_CC_IS_RDNA3(cc)) { 358 // High expert counts are almost always better on MMQ due to 359 // the synchronization overhead in the cuBLAS/hipBLAS path: 360 // https://github.com/ggml-org/llama.cpp/pull/18202 361 if (n_experts >= 64) { 362 return true; 363 } 364 365 // For some quantization types MMQ can have lower peak TOPS than hipBLAS 366 // so it's only faster for sufficiently small batch sizes: 367 switch (type) { 368 case GGML_TYPE_Q2_K: 369 return ne11 <= 128; 370 case GGML_TYPE_Q6_K: 371 return ne11 <= (GGML_CUDA_CC_IS_RDNA3_0(cc) ? 128 : 256); 372 case GGML_TYPE_IQ2_XS: 373 case GGML_TYPE_IQ2_S: 374 return GGML_CUDA_CC_IS_RDNA3_5(cc) || ne11 <= 128; 375 default: 376 return true; 377 } 378 } 379 380 // For RDNA4 MMQ is consistently faster than dequantization + hipBLAS: 381 // https://github.com/ggml-org/llama.cpp/pull/18537#issuecomment-3706422301 382 return true; 383 } 384 385 // gfx900 (Vega 10), gfx909, and gfx90c lack native dp4a, losing to dequant + hipBLAS 386 // for dense matrices; keep MMQ only for MoE, where the 387 // hipBLAS path is much slower. 388 if (cc == GGML_CUDA_CC_VEGA || GGML_CUDA_CC_IS_GCN_APU(cc)) { 389 return n_experts > 0; 390 } 391 392 return (!GGML_CUDA_CC_IS_CDNA(cc)) || ne11 < MMQ_DP4A_MAX_BATCH_SIZE; 393}