@@ -100,7 +100,7 @@ def cast_to_fp8(x: torch.Tensor):
100100 return x .to (torch .float8_e4m3fn )
101101
102102
103- def per_block_cast_to_fp8 (
103+ def per_block_cast_to_fp8_grouped (
104104 x : torch .Tensor , group_size : int
105105) -> tuple [torch .Tensor , torch .Tensor ]:
106106 is_2d = x .dim () == 2
@@ -247,6 +247,9 @@ def create_w8a8_fp8_per_block_weight(
247247
248248
249249class PerBlockFp8Weight (CompositeWeight , QuantWeight ):
250+ def _uses_direct_ue8m0 (self ) -> bool :
251+ return False
252+
250253 w8a8_weight_list : Dict [str , str ] = {
251254 W .attn_qkv_w : W .attn_qkv_s ,
252255 W .attn_o_w : W .attn_o_s ,
@@ -838,11 +841,19 @@ def _postprocess(
838841 )
839842 # kernel_weight, scale_weight = load_config.exported_device.convert_fp8_weight_params(kernel_weight, scale_weight)
840843
841- # Online SM100/ SM120 loading can already produce the final packed
844+ # Online SM120 loading can already produce the final packed
842845 # UE8M0 representation directly from source weights. Legacy/pre-quantized
843846 # inputs still arrive with floating-point block scales and require
844847 # the old dequantize/requantize conversion here.
845- if is_deep_gemm_e8m0_used () and scale_weight .dtype != torch .int32 :
848+ if self ._uses_direct_ue8m0 ():
849+ from rtp_llm .models_py .kernels .cuda .fp8_kernel import (
850+ pack_weight_scale_ue8m0 ,
851+ )
852+
853+ scale_weight = pack_weight_scale_ue8m0 (
854+ scale_weight , kernel_weight .shape [- 2 ]
855+ )
856+ elif is_deep_gemm_e8m0_used ():
846857 kernel_weight , scale_weight = requant_weight_ue8m0 (
847858 kernel_weight , scale_weight
848859 )
@@ -896,6 +907,16 @@ def __init__(
896907 self .kernel = kernel
897908 self .scale = scale
898909
910+ def _uses_direct_ue8m0 (self ) -> bool :
911+ from rtp_llm .models_py .utils .arch import is_sm12x
912+
913+ return (
914+ self .scale is not None
915+ and self .kernel .name not in (W .moe_w1 , W .moe_w2 )
916+ and self .group_size == 128
917+ and is_sm12x ()
918+ )
919+
899920 def _load_raw_tensor (
900921 self ,
901922 tensor_source : TensorSource ,
@@ -907,26 +928,23 @@ def _load_raw_tensor(
907928 tensor_source , layer_id , device , load_config
908929 )
909930
910- from rtp_llm .models_py .kernels .cuda .deepgemm_wrapper import (
911- is_deep_gemm_e8m0_used ,
912- )
913-
914- is_dense_weight = self .kernel .name not in (W .moe_w1 , W .moe_w2 )
915- direct_ue8m0 = (
916- self .scale is not None and is_dense_weight and is_deep_gemm_e8m0_used ()
917- )
918- if direct_ue8m0 and self .group_size != 128 :
919- raise ValueError (
920- "SM100/SM120 DeepGEMM packed UE8M0 requires group_size=128, "
921- f"got { self .group_size } for { self .kernel .name } "
922- )
931+ direct_ue8m0 = self ._uses_direct_ue8m0 ()
932+ if (
933+ self .scale is not None
934+ and self .kernel .name not in (W .moe_w1 , W .moe_w2 )
935+ and not direct_ue8m0
936+ ):
937+ from rtp_llm .models_py .utils .arch import is_sm12x
923938
939+ if is_sm12x () and self .group_size != 128 :
940+ raise ValueError (
941+ "SM120 DeepGEMM packed UE8M0 requires group_size=128, "
942+ f"got { self .group_size } for { self .kernel .name } "
943+ )
924944 res = {}
925945 scale = None
926946 if direct_ue8m0 :
927- from rtp_llm .models_py .kernels .cuda .fp8_kernel import (
928- quant_weight_ue8m0_packed ,
929- )
947+ from rtp_llm .models_py .kernels .cuda .fp8_kernel import quant_weight_ue8m0
930948
931949 source_weight = kernel .get (self .kernel .name )
932950 if source_weight .dim () != 2 :
@@ -936,11 +954,11 @@ def _load_raw_tensor(
936954 f"{ self .kernel .name } "
937955 )
938956 source_weight = source_weight .T
939- quant_kernel , scale = quant_weight_ue8m0_packed (
940- source_weight .contiguous ().to (device )
957+ quant_kernel , scale = quant_weight_ue8m0 (
958+ source_weight .contiguous ().to (device ), [ 128 , 128 ]
941959 )
942960 elif self .scale :
943- quant_kernel , scale = per_block_cast_to_fp8 (
961+ quant_kernel , scale = per_block_cast_to_fp8_grouped (
944962 kernel .get (self .kernel .name ), self .group_size
945963 )
946964 if quant_kernel .dim () == 2 :
@@ -956,10 +974,10 @@ def _load_raw_tensor(
956974 res = {self .kernel .name : quant_kernel .contiguous ().to (device )}
957975 if self .scale :
958976 scale = scale .T if scale .dim () == 2 and not direct_ue8m0 else scale
959- # Packed UE8M0 scales intentionally use a non-contiguous TMA
960- # layout (stride(-2) == 1). Do not normalize that layout here.
961- scale = scale . to ( device ) if direct_ue8m0 else scale . contiguous (). to ( device )
962- res .update ({self .scale .name : scale })
977+ # Keep ordinary [N/128, K/128] float scales through TP/DP/EP
978+ # splitting. _postprocess packs each rank's local scale into the
979+ # non-contiguous DeepGEMM TMA layout.
980+ res .update ({self .scale .name : scale . contiguous (). to ( device ) })
963981
964982 return res
965983
0 commit comments