[NPU] Adding a fast layernorm for diffusion models and fix BSA (#29027)
Co-authored-by: gemini-code-assist[bot] <176961590+gemini-code-assist[bot]@users.noreply.github.com> Co-authored-by: ronnie_zheng <zl19940307@163.com>
This commit is contained in:
co-authored by
gemini-code-assist[bot]
ronnie_zheng
parent
22d558b103
commit
2f22ed58ea
@@ -187,7 +187,7 @@ class BlockSparseAttentionImpl(AttentionImpl):
|
|||||||
smask: torch.Tensor,
|
smask: torch.Tensor,
|
||||||
sct: torch.Tensor,
|
sct: torch.Tensor,
|
||||||
) -> torch.Tensor:
|
) -> torch.Tensor:
|
||||||
return torch.ops.attentions.block_sparse_attention(
|
return torch.ops.attentions.ada_block_sparse_attention(
|
||||||
query=query,
|
query=query,
|
||||||
key=key,
|
key=key,
|
||||||
value=value,
|
value=value,
|
||||||
|
|||||||
@@ -425,7 +425,42 @@ class LayerNorm(CustomOp):
|
|||||||
# adapted from Diffusers: https://github.com/huggingface/diffusers/blob/main/src/diffusers/models/normalization.py
|
# adapted from Diffusers: https://github.com/huggingface/diffusers/blob/main/src/diffusers/models/normalization.py
|
||||||
# NOTE(will): Needed to match behavior of diffusers and wan2.1 even while using
|
# NOTE(will): Needed to match behavior of diffusers and wan2.1 even while using
|
||||||
# FSDP's MixedPrecisionPolicy
|
# FSDP's MixedPrecisionPolicy
|
||||||
class FP32LayerNorm(nn.LayerNorm):
|
@CustomOp.register("fp32_layer_norm")
|
||||||
|
class FP32LayerNorm(CustomOp, nn.LayerNorm):
|
||||||
|
|
||||||
|
def __init__(
|
||||||
|
self,
|
||||||
|
normalized_shape,
|
||||||
|
eps=1e-5,
|
||||||
|
elementwise_affine=True,
|
||||||
|
bias=True,
|
||||||
|
device=None,
|
||||||
|
dtype=None,
|
||||||
|
):
|
||||||
|
nn.LayerNorm.__init__(
|
||||||
|
self,
|
||||||
|
normalized_shape=normalized_shape,
|
||||||
|
eps=eps,
|
||||||
|
elementwise_affine=elementwise_affine,
|
||||||
|
bias=bias,
|
||||||
|
device=device,
|
||||||
|
dtype=dtype,
|
||||||
|
)
|
||||||
|
self._forward_method = self.dispatch_forward()
|
||||||
|
|
||||||
|
try:
|
||||||
|
import attentions # noqa: F401
|
||||||
|
except ImportError:
|
||||||
|
from sglang.multimodal_gen.runtime.utils.logging_utils import init_logger
|
||||||
|
|
||||||
|
logger = init_logger(__name__) # pylint: disable=invalid-name
|
||||||
|
logger.warning(
|
||||||
|
"The 'attentions' library is not installed. Falling back to native layernorm. "
|
||||||
|
"Installing this library may improve performance on NPU."
|
||||||
|
"See: sgl-project/sgl-kernel-npu"
|
||||||
|
)
|
||||||
|
self._forward_method = self.forward_native
|
||||||
|
|
||||||
def _cached_fp32_param(
|
def _cached_fp32_param(
|
||||||
self, attr: str, param: torch.Tensor | None, device: torch.device
|
self, attr: str, param: torch.Tensor | None, device: torch.device
|
||||||
) -> torch.Tensor | None:
|
) -> torch.Tensor | None:
|
||||||
@@ -452,7 +487,7 @@ class FP32LayerNorm(nn.LayerNorm):
|
|||||||
self.__dict__[attr] = (key, fp32_param)
|
self.__dict__[attr] = (key, fp32_param)
|
||||||
return fp32_param
|
return fp32_param
|
||||||
|
|
||||||
def forward(self, inputs: torch.Tensor) -> torch.Tensor:
|
def forward_native(self, inputs: torch.Tensor) -> torch.Tensor:
|
||||||
origin_dtype = inputs.dtype
|
origin_dtype = inputs.dtype
|
||||||
device = inputs.device
|
device = inputs.device
|
||||||
weight = self._cached_fp32_param("_weight_fp32_cache", self.weight, device)
|
weight = self._cached_fp32_param("_weight_fp32_cache", self.weight, device)
|
||||||
@@ -465,6 +500,25 @@ class FP32LayerNorm(nn.LayerNorm):
|
|||||||
self.eps,
|
self.eps,
|
||||||
).to(origin_dtype)
|
).to(origin_dtype)
|
||||||
|
|
||||||
|
def forward_cuda(self, inputs: torch.Tensor) -> torch.Tensor:
|
||||||
|
return self.forward_native(inputs)
|
||||||
|
|
||||||
|
def forward_npu(self, inputs: torch.Tensor) -> torch.Tensor:
|
||||||
|
origin_dtype = inputs.dtype
|
||||||
|
device = inputs.device
|
||||||
|
weight = self._cached_fp32_param("_weight_fp32_cache", self.weight, device)
|
||||||
|
bias = self._cached_fp32_param("_bias_fp32_cache", self.bias, device)
|
||||||
|
|
||||||
|
output, _, _ = torch.ops.attentions.layernorm(
|
||||||
|
input=inputs,
|
||||||
|
normalized_shape=list(self.normalized_shape),
|
||||||
|
weight=weight,
|
||||||
|
bias=bias,
|
||||||
|
eps=self.eps,
|
||||||
|
impl_mode=0,
|
||||||
|
)
|
||||||
|
return output.to(origin_dtype)
|
||||||
|
|
||||||
|
|
||||||
################################################################################
|
################################################################################
|
||||||
# Fused norm kernel
|
# Fused norm kernel
|
||||||
|
|||||||
Reference in New Issue
Block a user