feat(CRITICAL): 从 GitHub 扫描搬运 ixformer SDK + xllm 完整 GDN/MoE 代码
来源:
1. Chranos/ixformer (GitHub) → ixformer_sdk/ (230 files, 70K lines)
- inference/functions/vllm.py: vllm_moe_topk_softmax 完整实现 (2033 lines)
- inference/functions/moe.py: MoE ops 完整实现 (1380 lines)
- contrib/vllm_flash_attn/: FA2 Python 接口 (1018 lines)
- contrib/tgi/fused_moe.py: TGI fused MoE (429 lines)
- csrc/include/ixformer/: C++ kernel headers + cmake
2. Deep-Spark/xllm (GitHub) → upstream_ref/xllm_latest/ (+15 files)
- npu_torch/qwen3_5_decoder_layer_impl.cpp/.h
- npu_torch/qwen3_5_gated_delta_net.cpp/.h
- npu_torch/qwen3_next_*.cpp/.h (6 files)
- npu_torch/attention.cpp/.h + fused_moe.cpp/.h + CMakeLists.txt
- models/llm/qwen3_5.h + qwen3_5_mtp.h + qwen3_next.h
- models/vlm/qwen3_5.h
调用链完整性:
ixformer_sdk/inference/functions/vllm.py
→ ops.infer.moe_topk_softmax() (C++ 层)
→ 这就是 base 镜像 libixformer.so 里的实现
upstream_ref/xllm_latest/core/layers/ilu/fused_moe.cpp
→ ixformer::infer::topk_softmax() (直接 C++ 调用)
→ ixformer::infer::group_gemm() → 完整 7-step MoE pipeline
This commit is contained in:
@@ -0,0 +1,150 @@
|
||||
# coding=utf-8
|
||||
# Copyright 2018 The Google AI Language Team Authors and The HuggingFace Inc. team.
|
||||
# Copyright (c) 2018, NVIDIA CORPORATION. All rights reserved.
|
||||
#
|
||||
# Licensed under the Apache License, Version 2.0 (the "License");
|
||||
# you may not use this file except in compliance with the License.
|
||||
# You may obtain a copy of the License at
|
||||
#
|
||||
# http://www.apache.org/licenses/LICENSE-2.0
|
||||
#
|
||||
# Unless required by applicable law or agreed to in writing, software
|
||||
# distributed under the License is distributed on an "AS IS" BASIS,
|
||||
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
# See the License for the specific language governing permissions and
|
||||
# limitations under the License.
|
||||
"""BERT model configuration"""
|
||||
|
||||
from collections import OrderedDict
|
||||
from typing import Mapping
|
||||
|
||||
from transformers.configuration_utils import PretrainedConfig
|
||||
from transformers.onnx import OnnxConfig
|
||||
from transformers.utils import logging
|
||||
|
||||
logger = logging.get_logger(__name__)
|
||||
|
||||
|
||||
class BertConfig(PretrainedConfig):
|
||||
r"""
|
||||
This is the configuration class to store the configuration of a [`BertModel`] or a [`TFBertModel`]. It is used to
|
||||
instantiate a BERT model according to the specified arguments, defining the model architecture. Instantiating a
|
||||
configuration with the defaults will yield a similar configuration to that of the BERT
|
||||
[google-bert/bert-base-uncased](https://huggingface.co/google-bert/bert-base-uncased) architecture.
|
||||
|
||||
Configuration objects inherit from [`PretrainedConfig`] and can be used to control the model outputs. Read the
|
||||
documentation from [`PretrainedConfig`] for more information.
|
||||
|
||||
|
||||
Args:
|
||||
vocab_size (`int`, *optional*, defaults to 30522):
|
||||
Vocabulary size of the BERT model. Defines the number of different tokens that can be represented by the
|
||||
`inputs_ids` passed when calling [`BertModel`] or [`TFBertModel`].
|
||||
hidden_size (`int`, *optional*, defaults to 768):
|
||||
Dimensionality of the encoder layers and the pooler layer.
|
||||
num_hidden_layers (`int`, *optional*, defaults to 12):
|
||||
Number of hidden layers in the Transformer encoder.
|
||||
num_attention_heads (`int`, *optional*, defaults to 12):
|
||||
Number of attention heads for each attention layer in the Transformer encoder.
|
||||
intermediate_size (`int`, *optional*, defaults to 3072):
|
||||
Dimensionality of the "intermediate" (often named feed-forward) layer in the Transformer encoder.
|
||||
hidden_act (`str` or `Callable`, *optional*, defaults to `"gelu"`):
|
||||
The non-linear activation function (function or string) in the encoder and pooler. If string, `"gelu"`,
|
||||
`"relu"`, `"silu"` and `"gelu_new"` are supported.
|
||||
hidden_dropout_prob (`float`, *optional*, defaults to 0.1):
|
||||
The dropout probability for all fully connected layers in the embeddings, encoder, and pooler.
|
||||
attention_probs_dropout_prob (`float`, *optional*, defaults to 0.1):
|
||||
The dropout ratio for the attention probabilities.
|
||||
max_position_embeddings (`int`, *optional*, defaults to 512):
|
||||
The maximum sequence length that this model might ever be used with. Typically set this to something large
|
||||
just in case (e.g., 512 or 1024 or 2048).
|
||||
type_vocab_size (`int`, *optional*, defaults to 2):
|
||||
The vocabulary size of the `token_type_ids` passed when calling [`BertModel`] or [`TFBertModel`].
|
||||
initializer_range (`float`, *optional*, defaults to 0.02):
|
||||
The standard deviation of the truncated_normal_initializer for initializing all weight matrices.
|
||||
layer_norm_eps (`float`, *optional*, defaults to 1e-12):
|
||||
The epsilon used by the layer normalization layers.
|
||||
position_embedding_type (`str`, *optional*, defaults to `"absolute"`):
|
||||
Type of position embedding. Choose one of `"absolute"`, `"relative_key"`, `"relative_key_query"`. For
|
||||
positional embeddings use `"absolute"`. For more information on `"relative_key"`, please refer to
|
||||
[Self-Attention with Relative Position Representations (Shaw et al.)](https://arxiv.org/abs/1803.02155).
|
||||
For more information on `"relative_key_query"`, please refer to *Method 4* in [Improve Transformer Models
|
||||
with Better Relative Position Embeddings (Huang et al.)](https://arxiv.org/abs/2009.13658).
|
||||
is_decoder (`bool`, *optional*, defaults to `False`):
|
||||
Whether the model is used as a decoder or not. If `False`, the model is used as an encoder.
|
||||
use_cache (`bool`, *optional*, defaults to `True`):
|
||||
Whether or not the model should return the last key/values attentions (not used by all models). Only
|
||||
relevant if `config.is_decoder=True`.
|
||||
classifier_dropout (`float`, *optional*):
|
||||
The dropout ratio for the classification head.
|
||||
|
||||
Examples:
|
||||
|
||||
```python
|
||||
>>> from transformers import BertConfig, BertModel
|
||||
|
||||
>>> # Initializing a BERT google-bert/bert-base-uncased style configuration
|
||||
>>> configuration = BertConfig()
|
||||
|
||||
>>> # Initializing a model (with random weights) from the google-bert/bert-base-uncased style configuration
|
||||
>>> model = BertModel(configuration)
|
||||
|
||||
>>> # Accessing the model configuration
|
||||
>>> configuration = model.config
|
||||
```"""
|
||||
|
||||
model_type = "bert"
|
||||
|
||||
def __init__(
|
||||
self,
|
||||
vocab_size=30522,
|
||||
hidden_size=768,
|
||||
num_hidden_layers=12,
|
||||
num_attention_heads=12,
|
||||
intermediate_size=3072,
|
||||
hidden_act="gelu",
|
||||
hidden_dropout_prob=0.1,
|
||||
attention_probs_dropout_prob=0.1,
|
||||
max_position_embeddings=512,
|
||||
type_vocab_size=2,
|
||||
initializer_range=0.02,
|
||||
layer_norm_eps=1e-12,
|
||||
pad_token_id=0,
|
||||
position_embedding_type="absolute",
|
||||
use_cache=True,
|
||||
classifier_dropout=None,
|
||||
**kwargs,
|
||||
):
|
||||
super().__init__(pad_token_id=pad_token_id, **kwargs)
|
||||
|
||||
self.vocab_size = vocab_size
|
||||
self.hidden_size = hidden_size
|
||||
self.num_hidden_layers = num_hidden_layers
|
||||
self.num_attention_heads = num_attention_heads
|
||||
self.hidden_act = hidden_act
|
||||
self.intermediate_size = intermediate_size
|
||||
self.hidden_dropout_prob = hidden_dropout_prob
|
||||
self.attention_probs_dropout_prob = attention_probs_dropout_prob
|
||||
self.max_position_embeddings = max_position_embeddings
|
||||
self.type_vocab_size = type_vocab_size
|
||||
self.initializer_range = initializer_range
|
||||
self.layer_norm_eps = layer_norm_eps
|
||||
self.position_embedding_type = position_embedding_type
|
||||
self.use_cache = use_cache
|
||||
self.classifier_dropout = classifier_dropout
|
||||
|
||||
|
||||
class BertOnnxConfig(OnnxConfig):
|
||||
@property
|
||||
def inputs(self) -> Mapping[str, Mapping[int, str]]:
|
||||
if self.task == "multiple-choice":
|
||||
dynamic_axis = {0: "batch", 1: "choice", 2: "sequence"}
|
||||
else:
|
||||
dynamic_axis = {0: "batch", 1: "sequence"}
|
||||
return OrderedDict(
|
||||
[
|
||||
("input_ids", dynamic_axis),
|
||||
("attention_mask", dynamic_axis),
|
||||
("token_type_ids", dynamic_axis),
|
||||
]
|
||||
)
|
||||
2145
ixformer_sdk/contrib/transformers/models/bert/modeling_bert.py
Normal file
2145
ixformer_sdk/contrib/transformers/models/bert/modeling_bert.py
Normal file
File diff suppressed because it is too large
Load Diff
174
ixformer_sdk/contrib/transformers/models/t5/configuration_t5.py
Normal file
174
ixformer_sdk/contrib/transformers/models/t5/configuration_t5.py
Normal file
@@ -0,0 +1,174 @@
|
||||
# coding=utf-8
|
||||
# Copyright 2020, The T5 Authors and HuggingFace Inc.
|
||||
#
|
||||
# Licensed under the Apache License, Version 2.0 (the "License");
|
||||
# you may not use this file except in compliance with the License.
|
||||
# You may obtain a copy of the License at
|
||||
#
|
||||
# http://www.apache.org/licenses/LICENSE-2.0
|
||||
#
|
||||
# Unless required by applicable law or agreed to in writing, software
|
||||
# distributed under the License is distributed on an "AS IS" BASIS,
|
||||
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
# See the License for the specific language governing permissions and
|
||||
# limitations under the License.
|
||||
""" T5 model configuration"""
|
||||
from typing import Mapping
|
||||
|
||||
from transformers.configuration_utils import PretrainedConfig
|
||||
from transformers.onnx import OnnxSeq2SeqConfigWithPast
|
||||
from transformers.utils import logging
|
||||
|
||||
logger = logging.get_logger(__name__)
|
||||
|
||||
T5_PRETRAINED_CONFIG_ARCHIVE_MAP = {
|
||||
"t5-small": "https://huggingface.co/t5-small/resolve/main/config.json",
|
||||
"t5-base": "https://huggingface.co/t5-base/resolve/main/config.json",
|
||||
"t5-large": "https://huggingface.co/t5-large/resolve/main/config.json",
|
||||
"t5-3b": "https://huggingface.co/t5-3b/resolve/main/config.json",
|
||||
"t5-11b": "https://huggingface.co/t5-11b/resolve/main/config.json",
|
||||
}
|
||||
|
||||
|
||||
class T5Config(PretrainedConfig):
|
||||
r"""
|
||||
This is the configuration class to store the configuration of a [`T5Model`] or a [`TFT5Model`]. It is used to
|
||||
instantiate a T5 model according to the specified arguments, defining the model architecture. Instantiating a
|
||||
configuration with the defaults will yield a similar configuration to that of the T5
|
||||
[t5-small](https://huggingface.co/t5-small) architecture.
|
||||
|
||||
Configuration objects inherit from [`PretrainedConfig`] and can be used to control the model outputs. Read the
|
||||
documentation from [`PretrainedConfig`] for more information.
|
||||
|
||||
Arguments:
|
||||
vocab_size (`int`, *optional*, defaults to 32128):
|
||||
Vocabulary size of the T5 model. Defines the number of different tokens that can be represented by the
|
||||
`inputs_ids` passed when calling [`T5Model`] or [`TFT5Model`].
|
||||
d_model (`int`, *optional*, defaults to 512):
|
||||
Size of the encoder layers and the pooler layer.
|
||||
d_kv (`int`, *optional*, defaults to 64):
|
||||
Size of the key, query, value projections per attention head. The `inner_dim` of the projection layer will
|
||||
be defined as `num_heads * d_kv`.
|
||||
d_ff (`int`, *optional*, defaults to 2048):
|
||||
Size of the intermediate feed forward layer in each `T5Block`.
|
||||
num_layers (`int`, *optional*, defaults to 6):
|
||||
Number of hidden layers in the Transformer encoder.
|
||||
num_decoder_layers (`int`, *optional*):
|
||||
Number of hidden layers in the Transformer decoder. Will use the same value as `num_layers` if not set.
|
||||
num_heads (`int`, *optional*, defaults to 8):
|
||||
Number of attention heads for each attention layer in the Transformer encoder.
|
||||
relative_attention_num_buckets (`int`, *optional*, defaults to 32):
|
||||
The number of buckets to use for each attention layer.
|
||||
relative_attention_max_distance (`int`, *optional*, defaults to 128):
|
||||
The maximum distance of the longer sequences for the bucket separation.
|
||||
dropout_rate (`float`, *optional*, defaults to 0.1):
|
||||
The ratio for all dropout layers.
|
||||
layer_norm_eps (`float`, *optional*, defaults to 1e-6):
|
||||
The epsilon used by the layer normalization layers.
|
||||
initializer_factor (`float`, *optional*, defaults to 1):
|
||||
A factor for initializing all weight matrices (should be kept to 1, used internally for initialization
|
||||
testing).
|
||||
feed_forward_proj (`string`, *optional*, defaults to `"relu"`):
|
||||
Type of feed forward layer to be used. Should be one of `"relu"` or `"gated-gelu"`. T5v1.1 uses the
|
||||
`"gated-gelu"` feed forward projection. Original T5 uses `"relu"`.
|
||||
use_cache (`bool`, *optional*, defaults to `True`):
|
||||
Whether or not the model should return the last key/values attentions (not used by all models).
|
||||
"""
|
||||
model_type = "t5"
|
||||
keys_to_ignore_at_inference = ["past_key_values"]
|
||||
attribute_map = {
|
||||
"hidden_size": "d_model",
|
||||
"num_attention_heads": "num_heads",
|
||||
"num_hidden_layers": "num_layers",
|
||||
}
|
||||
|
||||
def __init__(
|
||||
self,
|
||||
vocab_size=32128,
|
||||
d_model=512,
|
||||
d_kv=64,
|
||||
d_ff=2048,
|
||||
num_layers=6,
|
||||
num_decoder_layers=None,
|
||||
num_heads=8,
|
||||
relative_attention_num_buckets=32,
|
||||
relative_attention_max_distance=128,
|
||||
dropout_rate=0.1,
|
||||
layer_norm_epsilon=1e-6,
|
||||
initializer_factor=1.0,
|
||||
feed_forward_proj="relu",
|
||||
is_encoder_decoder=True,
|
||||
use_cache=True,
|
||||
pad_token_id=0,
|
||||
eos_token_id=1,
|
||||
**kwargs,
|
||||
):
|
||||
self.vocab_size = vocab_size
|
||||
self.d_model = d_model
|
||||
self.d_kv = d_kv
|
||||
self.d_ff = d_ff
|
||||
self.num_layers = num_layers
|
||||
self.num_decoder_layers = (
|
||||
num_decoder_layers if num_decoder_layers is not None else self.num_layers
|
||||
) # default = symmetry
|
||||
self.num_heads = num_heads
|
||||
self.relative_attention_num_buckets = relative_attention_num_buckets
|
||||
self.relative_attention_max_distance = relative_attention_max_distance
|
||||
self.dropout_rate = dropout_rate
|
||||
self.layer_norm_epsilon = layer_norm_epsilon
|
||||
self.initializer_factor = initializer_factor
|
||||
self.feed_forward_proj = feed_forward_proj
|
||||
self.use_cache = use_cache
|
||||
|
||||
act_info = self.feed_forward_proj.split("-")
|
||||
self.dense_act_fn = act_info[-1]
|
||||
self.is_gated_act = act_info[0] == "gated"
|
||||
|
||||
if len(act_info) > 1 and act_info[0] != "gated" or len(act_info) > 2:
|
||||
raise ValueError(
|
||||
f"`feed_forward_proj`: {feed_forward_proj} is not a valid activation function of the dense layer."
|
||||
"Please make sure `feed_forward_proj` is of the format `gated-{ACT_FN}` or `{ACT_FN}`, e.g. "
|
||||
"'gated-gelu' or 'relu'"
|
||||
)
|
||||
|
||||
# for backwards compatibility
|
||||
if feed_forward_proj == "gated-gelu":
|
||||
self.dense_act_fn = "gelu_new"
|
||||
|
||||
super().__init__(
|
||||
pad_token_id=pad_token_id,
|
||||
eos_token_id=eos_token_id,
|
||||
is_encoder_decoder=is_encoder_decoder,
|
||||
**kwargs,
|
||||
)
|
||||
|
||||
|
||||
class T5OnnxConfig(OnnxSeq2SeqConfigWithPast):
|
||||
@property
|
||||
def inputs(self) -> Mapping[str, Mapping[int, str]]:
|
||||
common_inputs = {
|
||||
"input_ids": {0: "batch", 1: "encoder_sequence"},
|
||||
"attention_mask": {0: "batch", 1: "encoder_sequence"},
|
||||
}
|
||||
if self.use_past:
|
||||
common_inputs["attention_mask"][1] = "past_encoder_sequence + sequence"
|
||||
common_inputs["decoder_input_ids"] = {0: "batch"}
|
||||
common_inputs["decoder_attention_mask"] = {
|
||||
0: "batch",
|
||||
1: "past_decoder_sequence + sequence",
|
||||
}
|
||||
else:
|
||||
common_inputs["decoder_input_ids"] = {0: "batch", 1: "decoder_sequence"}
|
||||
common_inputs["decoder_attention_mask"] = {
|
||||
0: "batch",
|
||||
1: "decoder_sequence",
|
||||
}
|
||||
|
||||
if self.use_past:
|
||||
self.fill_with_past_key_values_(common_inputs, direction="inputs")
|
||||
|
||||
return common_inputs
|
||||
|
||||
@property
|
||||
def default_onnx_opset(self) -> int:
|
||||
return 13
|
||||
@@ -0,0 +1,315 @@
|
||||
import torch
|
||||
from transformers.activations import NewGELUActivation
|
||||
|
||||
import ixformer
|
||||
|
||||
|
||||
def self_attention_forward(
|
||||
self,
|
||||
hidden_states,
|
||||
attention_mask=None,
|
||||
position_bias=None,
|
||||
layer_head_mask=None,
|
||||
past_key_value=None,
|
||||
use_cache=False,
|
||||
output_attentions=False,
|
||||
):
|
||||
assert output_attentions is False
|
||||
assert layer_head_mask is None
|
||||
|
||||
normed_hidden_states = self.layer_norm(hidden_states)
|
||||
|
||||
if not hasattr(self, "qkv_weight"):
|
||||
self.qkv_weight = torch.cat(
|
||||
[
|
||||
self.SelfAttention.q.weight,
|
||||
self.SelfAttention.k.weight,
|
||||
self.SelfAttention.v.weight,
|
||||
],
|
||||
dim=0,
|
||||
)
|
||||
self.qkv_bias = None
|
||||
|
||||
del self.SelfAttention.q.weight
|
||||
del self.SelfAttention.k.weight
|
||||
del self.SelfAttention.v.weight
|
||||
|
||||
batch_size, seq_length = hidden_states.shape[:2]
|
||||
real_seq_length = seq_length
|
||||
if past_key_value is not None:
|
||||
if len(past_key_value) != 2:
|
||||
raise ValueError(
|
||||
f"past_key_value should have 2 past states: keys and values. Got { len(past_key_value)} past states"
|
||||
)
|
||||
real_seq_length += past_key_value[0].shape[2]
|
||||
key_length = real_seq_length
|
||||
|
||||
def unshape(states):
|
||||
"""reshape"""
|
||||
return (
|
||||
states.transpose(1, 2)
|
||||
.contiguous()
|
||||
.view(batch_size, -1, self.SelfAttention.inner_dim)
|
||||
)
|
||||
|
||||
qkv = ixformer.functions.linear(
|
||||
normed_hidden_states, self.qkv_weight, self.qkv_bias
|
||||
)
|
||||
|
||||
if past_key_value is not None:
|
||||
pask_key, past_value = past_key_value
|
||||
(
|
||||
query_states,
|
||||
key_states,
|
||||
value_states,
|
||||
) = ixformer.functions.t5_split_qkv_update_kv_cache(
|
||||
qkv,
|
||||
pask_key,
|
||||
past_value,
|
||||
self.SelfAttention.n_heads,
|
||||
self.SelfAttention.key_value_proj_dim,
|
||||
)
|
||||
else:
|
||||
query_states, key_states, value_states = ixformer.functions.t5_split_qkv(
|
||||
qkv, self.SelfAttention.n_heads, self.SelfAttention.key_value_proj_dim
|
||||
)
|
||||
|
||||
if position_bias is None:
|
||||
if not self.SelfAttention.has_relative_attention_bias:
|
||||
position_bias = torch.zeros(
|
||||
(1, self.SelfAttention.n_heads, real_seq_length, key_length),
|
||||
device=query_states.device,
|
||||
dtype=query_states.dtype,
|
||||
)
|
||||
else:
|
||||
position_bias = self.SelfAttention.compute_bias(
|
||||
real_seq_length, key_length, device=query_states.device
|
||||
)
|
||||
|
||||
# if key and values are already calculated
|
||||
# we want only the last query position bias
|
||||
if past_key_value is not None:
|
||||
position_bias = position_bias[:, :, -hidden_states.size(1) :, :]
|
||||
|
||||
if attention_mask is not None:
|
||||
# (batch_size, n_heads, seq_length, key_length)
|
||||
position_bias = position_bias + attention_mask
|
||||
|
||||
if self.SelfAttention.pruned_heads:
|
||||
mask = torch.ones(position_bias.shape[1])
|
||||
mask[list(self.pruned_heads)] = 0
|
||||
position_bias_masked = position_bias[:, mask.bool()]
|
||||
else:
|
||||
position_bias_masked = position_bias
|
||||
|
||||
attn_output = ixformer.functions.ixinfer_flash_attn_pad(
|
||||
query_states.contiguous(),
|
||||
key_states.contiguous(),
|
||||
value_states.contiguous(),
|
||||
mask=position_bias_masked.float().contiguous(),
|
||||
atten_scale=1,
|
||||
)
|
||||
attn_output = unshape(attn_output)
|
||||
|
||||
attn_output = self.SelfAttention.o(attn_output)
|
||||
|
||||
present_key_value_state = (
|
||||
(key_states, value_states)
|
||||
if (self.SelfAttention.is_decoder and use_cache)
|
||||
else None
|
||||
)
|
||||
outputs = (attn_output,) + (present_key_value_state,) + (position_bias,)
|
||||
|
||||
if output_attentions:
|
||||
outputs = outputs + (None,)
|
||||
hidden_states = attn_output + hidden_states
|
||||
outputs = (hidden_states,) + outputs[1:]
|
||||
|
||||
return outputs
|
||||
|
||||
|
||||
def cross_attention_forward(
|
||||
self,
|
||||
hidden_states,
|
||||
key_value_states,
|
||||
attention_mask=None,
|
||||
position_bias=None,
|
||||
layer_head_mask=None,
|
||||
past_key_value=None,
|
||||
use_cache=False,
|
||||
query_length=None,
|
||||
output_attentions=False,
|
||||
):
|
||||
|
||||
assert output_attentions is False
|
||||
assert layer_head_mask is None
|
||||
|
||||
def unshape(states):
|
||||
"""reshape"""
|
||||
return (
|
||||
states.transpose(1, 2)
|
||||
.contiguous()
|
||||
.view(batch_size, -1, self.EncDecAttention.inner_dim)
|
||||
)
|
||||
|
||||
normed_hidden_states = self.layer_norm(hidden_states)
|
||||
|
||||
# cross attn need key_value_states
|
||||
assert key_value_states is not None
|
||||
batch_size, seq_length = hidden_states.shape[:2]
|
||||
real_seq_length = seq_length
|
||||
|
||||
if past_key_value is not None:
|
||||
if len(past_key_value) != 2:
|
||||
raise ValueError(
|
||||
f"past_key_value should have 2 past states: keys and values. Got { len(past_key_value)} past states"
|
||||
)
|
||||
real_seq_length += (
|
||||
past_key_value[0].shape[2] if query_length is None else query_length
|
||||
)
|
||||
|
||||
key_length = (
|
||||
real_seq_length if key_value_states is None else key_value_states.shape[1]
|
||||
)
|
||||
head_num, head_dim = (
|
||||
self.EncDecAttention.n_heads,
|
||||
self.EncDecAttention.key_value_proj_dim,
|
||||
)
|
||||
|
||||
query_states = (
|
||||
self.EncDecAttention.q(normed_hidden_states)
|
||||
.view(batch_size, seq_length, head_num, head_dim)
|
||||
.transpose(1, 2)
|
||||
.contiguous()
|
||||
)
|
||||
|
||||
if past_key_value is not None:
|
||||
if past_key_value[0].shape[2] != key_value_states.shape[1]:
|
||||
# checking that the `sequence_length` of the `past_key_value` is the same as
|
||||
# the provided `key_value_states` to support prefix tuning
|
||||
# cross-attn
|
||||
# (batch_size, n_heads, seq_length, dim_per_head)
|
||||
key_states = (
|
||||
self.EncDecAttention.k(key_value_states)
|
||||
.view(batch_size, key_length, head_num, head_dim)
|
||||
.transpose(1, 2)
|
||||
)
|
||||
value_states = (
|
||||
self.EncDecAttention.v(key_value_states)
|
||||
.view(batch_size, key_length, head_num, head_dim)
|
||||
.transpose(1, 2)
|
||||
)
|
||||
else:
|
||||
# cross-attn
|
||||
key_states = past_key_value[0]
|
||||
value_states = past_key_value[1]
|
||||
else:
|
||||
key_states = (
|
||||
self.EncDecAttention.k(key_value_states)
|
||||
.view(batch_size, key_length, head_num, head_dim)
|
||||
.transpose(1, 2)
|
||||
)
|
||||
value_states = (
|
||||
self.EncDecAttention.v(key_value_states)
|
||||
.view(batch_size, key_length, head_num, head_dim)
|
||||
.transpose(1, 2)
|
||||
)
|
||||
|
||||
if not query_states.is_contiguous():
|
||||
query_states = query_states.contiguous()
|
||||
|
||||
# TODO: fix this bug
|
||||
if not value_states.is_contiguous():
|
||||
new_value_states = query_states.new_empty(value_states.shape)
|
||||
new_value_states.copy_(value_states)
|
||||
value_states = new_value_states
|
||||
if not key_states.is_contiguous():
|
||||
numel = torch.numel(key_states)
|
||||
new_key_states = query_states.new_empty([numel * 2])[:numel].view(
|
||||
*list(key_states.shape)
|
||||
)
|
||||
new_key_states.copy_(key_states)
|
||||
key_states = new_key_states
|
||||
|
||||
if position_bias is None:
|
||||
if not self.EncDecAttention.has_relative_attention_bias:
|
||||
position_bias = torch.zeros(
|
||||
(1, self.EncDecAttention.n_heads, real_seq_length, key_length),
|
||||
device=query_states.device,
|
||||
dtype=query_states.dtype,
|
||||
)
|
||||
else:
|
||||
position_bias = self.EncDecAttention.compute_bias(
|
||||
real_seq_length, key_length, device=query_states.device
|
||||
)
|
||||
|
||||
# if key and values are already calculated
|
||||
# we want only the last query position bias
|
||||
if past_key_value is not None:
|
||||
position_bias = position_bias[:, :, -hidden_states.size(1) :, :]
|
||||
|
||||
if attention_mask is not None:
|
||||
# (batch_size, n_heads, seq_length, key_length)
|
||||
position_bias = position_bias + attention_mask
|
||||
|
||||
if self.EncDecAttention.pruned_heads:
|
||||
mask = torch.ones(position_bias.shape[1])
|
||||
mask[list(self.pruned_heads)] = 0
|
||||
position_bias_masked = position_bias[:, mask.bool()]
|
||||
else:
|
||||
position_bias_masked = position_bias
|
||||
|
||||
attn_output = ixformer.functions.ixinfer_flash_attn_pad(
|
||||
query_states,
|
||||
key_states.contiguous(),
|
||||
value_states.contiguous(),
|
||||
mask=position_bias_masked.float().contiguous(),
|
||||
atten_scale=1,
|
||||
)
|
||||
attn_output = unshape(attn_output)
|
||||
|
||||
attn_output = self.EncDecAttention.o(attn_output)
|
||||
|
||||
present_key_value_state = (
|
||||
(key_states, value_states)
|
||||
if (self.EncDecAttention.is_decoder and use_cache)
|
||||
else None
|
||||
)
|
||||
outputs = (attn_output,) + (present_key_value_state,) + (position_bias,)
|
||||
|
||||
if output_attentions:
|
||||
outputs = outputs + (None,)
|
||||
hidden_states = attn_output + hidden_states
|
||||
outputs = (hidden_states,) + outputs[1:]
|
||||
|
||||
return outputs
|
||||
|
||||
|
||||
def dense_gated_act_dense_forward(self, hidden_states):
|
||||
if isinstance(self.act, NewGELUActivation):
|
||||
if not hasattr(self, "wi"):
|
||||
self.wi = torch.cat([self.wi_1.weight, self.wi_0.weight], dim=0)
|
||||
del self.wi_1
|
||||
del self.wi_0
|
||||
hidden_states = ixformer.functions.linear(hidden_states, self.wi, None)
|
||||
hidden_states = ixformer.functions.gelu_and_mul(hidden_states)
|
||||
hidden_states = ixformer.functions.linear(hidden_states, self.wo.weight, None)
|
||||
else:
|
||||
hidden_gelu = self.act(self.wi_0(hidden_states))
|
||||
hidden_linear = self.wi_1(hidden_states)
|
||||
hidden_states = hidden_gelu * hidden_linear
|
||||
|
||||
hidden_states = self.dropout(hidden_states)
|
||||
|
||||
# To make 8bit quantization work for google/flan-t5-xxl, self.wo is kept in float32.
|
||||
# See https://github.com/huggingface/transformers/issues/20287
|
||||
# we also make sure the weights are not in `int8` in case users will force `_keep_in_fp32_modules` to be `None``
|
||||
if (
|
||||
isinstance(self.wo.weight, torch.Tensor)
|
||||
and hidden_states.dtype != self.wo.weight.dtype
|
||||
and self.wo.weight.dtype != torch.int8
|
||||
):
|
||||
hidden_states = hidden_states.to(self.wo.weight.dtype)
|
||||
|
||||
hidden_states = self.wo(hidden_states)
|
||||
return hidden_states
|
||||
2644
ixformer_sdk/contrib/transformers/models/t5/modeling_t5.py
Normal file
2644
ixformer_sdk/contrib/transformers/models/t5/modeling_t5.py
Normal file
File diff suppressed because it is too large
Load Diff
Reference in New Issue
Block a user