mirror of
https://github.com/linkedin/Liger-Kernel.git
synced 2026-10-12 02:17:47 +00:00
Support transfomers v5 (#994)
>[!IMPORTANT] >Do not merge this PR before all issues are resolved! > >Testing with three versions: `4.52.0` , `4.57.6` and the latest stable version >[!NOTE] >nvi-ci is split into correctness test ci and convergence test ci to speed up testing in this PR >, and more jobs for testing bc with transformers v4 (4.49.0 and 4.57.6) > >Whether keeping this change or not is yet to be discussed ## Summary <!--- This is a required section; please describe the main purpose of this proposed code change. ---> This is a dev branch for aggregating PRs related to transformers v5 changes. <!--- ## Details This is an optional section; is there anything specific that reviewers should be aware of? ---> ## Testing Done <!--- This is a required section; please describe how this change was tested. ---> <!-- Replace BLANK with your device type. For example, A100-80G-PCIe Complete the following tasks before sending your PR, and replace `[ ]` with `[x]` to indicate you have done them. --> - Hardware Type: <BLANK> - [x] run `make test` to ensure correctness - [x] run `make checkstyle` to ensure code style - [x] run `make test-convergence` to ensure convergence --------- Signed-off-by: Tcc0403 <[email protected]> Co-authored-by: Yunwei Dai <[email protected]> Co-authored-by: Vaibhav Jindal <[email protected]> Co-authored-by: Yuki Uehara <[email protected]> Co-authored-by: Chun-Mao Lai <[email protected]> Co-authored-by: Vaibhav Jindal <[email protected]> Co-authored-by: Michael Lai <[email protected]>
This commit is contained in:
co-authored by
Yunwei Dai
Vaibhav Jindal
Yuki Uehara
Chun-Mao Lai
Vaibhav Jindal
Michael Lai
parent
7d82f73d1e
commit
175cdf0e37
@@ -46,7 +46,7 @@ jobs:
|
||||
- name: Run checkstyle
|
||||
run: make checkstyle
|
||||
|
||||
tests:
|
||||
correctness-tests:
|
||||
runs-on: ubuntu-latest
|
||||
needs: [checkstyle]
|
||||
env:
|
||||
@@ -69,15 +69,14 @@ jobs:
|
||||
|
||||
- name: Run tests
|
||||
run: |
|
||||
modal run dev.modal.tests
|
||||
modal run dev.modal.tests::liger_correctness_tests
|
||||
|
||||
tests-bwd:
|
||||
convergence-tests:
|
||||
runs-on: ubuntu-latest
|
||||
needs: [checkstyle]
|
||||
env:
|
||||
MODAL_TOKEN_ID: ${{ secrets.MODAL_TOKEN_ID }}
|
||||
MODAL_TOKEN_SECRET: ${{ secrets.MODAL_TOKEN_SECRET }}
|
||||
REBUILD_IMAGE: ${{ github.event_name == 'schedule' || github.event_name == 'workflow_dispatch' }}
|
||||
|
||||
steps:
|
||||
- name: Checkout code
|
||||
@@ -95,4 +94,109 @@ jobs:
|
||||
|
||||
- name: Run tests
|
||||
run: |
|
||||
modal run dev.modal.tests_bwd
|
||||
modal run dev.modal.tests::liger_convergence_tests
|
||||
|
||||
|
||||
correctness-tests-with-transformers-4-52-0:
|
||||
runs-on: ubuntu-latest
|
||||
needs: [checkstyle]
|
||||
env:
|
||||
MODAL_TOKEN_ID: ${{ secrets.MODAL_TOKEN_ID }}
|
||||
MODAL_TOKEN_SECRET: ${{ secrets.MODAL_TOKEN_SECRET }}
|
||||
|
||||
steps:
|
||||
- name: Checkout code
|
||||
uses: actions/checkout@v6
|
||||
|
||||
- name: Set up Python
|
||||
uses: actions/setup-python@v6
|
||||
with:
|
||||
python-version: '3.10'
|
||||
|
||||
- name: Install dependencies
|
||||
run: |
|
||||
python -m pip install --upgrade pip
|
||||
pip install modal
|
||||
|
||||
- name: Run tests
|
||||
run: |
|
||||
modal run dev.modal.tests::liger_oldest_v4_correctness_tests
|
||||
|
||||
|
||||
|
||||
convergence-tests-with-transformers-4-52-0:
|
||||
runs-on: ubuntu-latest
|
||||
needs: [checkstyle]
|
||||
env:
|
||||
MODAL_TOKEN_ID: ${{ secrets.MODAL_TOKEN_ID }}
|
||||
MODAL_TOKEN_SECRET: ${{ secrets.MODAL_TOKEN_SECRET }}
|
||||
|
||||
steps:
|
||||
- name: Checkout code
|
||||
uses: actions/checkout@v6
|
||||
|
||||
- name: Set up Python
|
||||
uses: actions/setup-python@v6
|
||||
with:
|
||||
python-version: '3.10'
|
||||
|
||||
- name: Install dependencies
|
||||
run: |
|
||||
python -m pip install --upgrade pip
|
||||
pip install modal
|
||||
|
||||
- name: Run tests
|
||||
run: |
|
||||
modal run dev.modal.tests::liger_oldest_v4_convergence_tests
|
||||
|
||||
correctness-tests-with-transformers-4-57-6:
|
||||
runs-on: ubuntu-latest
|
||||
needs: [checkstyle]
|
||||
env:
|
||||
MODAL_TOKEN_ID: ${{ secrets.MODAL_TOKEN_ID }}
|
||||
MODAL_TOKEN_SECRET: ${{ secrets.MODAL_TOKEN_SECRET }}
|
||||
|
||||
steps:
|
||||
- name: Checkout code
|
||||
uses: actions/checkout@v6
|
||||
|
||||
- name: Set up Python
|
||||
uses: actions/setup-python@v6
|
||||
with:
|
||||
python-version: '3.10'
|
||||
|
||||
- name: Install dependencies
|
||||
run: |
|
||||
python -m pip install --upgrade pip
|
||||
pip install modal
|
||||
|
||||
- name: Run tests
|
||||
run: |
|
||||
modal run dev.modal.tests::liger_latest_v4_correctness_tests
|
||||
|
||||
|
||||
|
||||
convergence-tests-with-transformers-4-57-6:
|
||||
runs-on: ubuntu-latest
|
||||
needs: [checkstyle]
|
||||
env:
|
||||
MODAL_TOKEN_ID: ${{ secrets.MODAL_TOKEN_ID }}
|
||||
MODAL_TOKEN_SECRET: ${{ secrets.MODAL_TOKEN_SECRET }}
|
||||
|
||||
steps:
|
||||
- name: Checkout code
|
||||
uses: actions/checkout@v6
|
||||
|
||||
- name: Set up Python
|
||||
uses: actions/setup-python@v6
|
||||
with:
|
||||
python-version: '3.10'
|
||||
|
||||
- name: Install dependencies
|
||||
run: |
|
||||
python -m pip install --upgrade pip
|
||||
pip install modal
|
||||
|
||||
- name: Run tests
|
||||
run: |
|
||||
modal run dev.modal.tests::liger_latest_v4_convergence_tests
|
||||
@@ -40,8 +40,6 @@ def bench_speed_llama4_rope(input: SingleBenchmarkRunInput) -> SingleBenchmarkRu
|
||||
num_key_value_heads=num_kv_heads,
|
||||
head_dim=head_dim,
|
||||
max_position_embeddings=seq_len,
|
||||
rope_theta=10000.0,
|
||||
rope_scaling=None, # Use default rope type
|
||||
)
|
||||
|
||||
rotary_emb = transformers_version_dispatch(
|
||||
@@ -134,8 +132,6 @@ def bench_memory_llama4_rope(input: SingleBenchmarkRunInput) -> SingleBenchmarkR
|
||||
num_key_value_heads=num_kv_heads,
|
||||
head_dim=head_dim,
|
||||
max_position_embeddings=seq_len,
|
||||
rope_theta=10000.0,
|
||||
rope_scaling=None, # Use default rope type
|
||||
)
|
||||
|
||||
rotary_emb = transformers_version_dispatch(
|
||||
|
||||
+97
-1
@@ -6,6 +6,8 @@ ROOT_PATH = Path(__file__).parent.parent.parent
|
||||
REMOTE_ROOT_PATH = "/root/liger-kernel"
|
||||
PYTHON_VERSION = "3.12"
|
||||
|
||||
OLDEST_SUPPORTED_TRANSFORMERS_V4_VERSION = "4.52.0"
|
||||
|
||||
image = modal.Image.debian_slim(python_version=PYTHON_VERSION).pip_install("uv")
|
||||
|
||||
app = modal.App("liger_tests", image=image)
|
||||
@@ -15,7 +17,7 @@ repo = image.add_local_dir(ROOT_PATH, remote_path=REMOTE_ROOT_PATH)
|
||||
|
||||
|
||||
@app.function(gpu="H100!", image=repo, timeout=90 * 60)
|
||||
def liger_tests():
|
||||
def liger_correctness_tests():
|
||||
import subprocess
|
||||
|
||||
subprocess.run(
|
||||
@@ -25,4 +27,98 @@ def liger_tests():
|
||||
cwd=REMOTE_ROOT_PATH,
|
||||
)
|
||||
subprocess.run(["make test"], check=True, shell=True, cwd=REMOTE_ROOT_PATH)
|
||||
|
||||
|
||||
@app.function(gpu="H100!", image=repo, timeout=90 * 60)
|
||||
def liger_convergence_tests():
|
||||
import subprocess
|
||||
|
||||
subprocess.run(
|
||||
["uv pip install -e '.[dev]' --system"],
|
||||
check=True,
|
||||
shell=True,
|
||||
cwd=REMOTE_ROOT_PATH,
|
||||
)
|
||||
subprocess.run(["make test-convergence"], check=True, shell=True, cwd=REMOTE_ROOT_PATH)
|
||||
|
||||
|
||||
oldest_v4_app = modal.App("liger_oldest_v4_tests", image=image) # 4.52.0
|
||||
|
||||
|
||||
@oldest_v4_app.function(gpu="H100!", image=repo, timeout=90 * 60)
|
||||
def liger_oldest_v4_correctness_tests():
|
||||
import subprocess
|
||||
|
||||
subprocess.run(
|
||||
["uv pip install -e '.[dev]' --system"],
|
||||
check=True,
|
||||
shell=True,
|
||||
cwd=REMOTE_ROOT_PATH,
|
||||
)
|
||||
subprocess.run(
|
||||
[f"uv pip install 'transformers=={OLDEST_SUPPORTED_TRANSFORMERS_V4_VERSION}' --system"],
|
||||
check=True,
|
||||
shell=True,
|
||||
cwd=REMOTE_ROOT_PATH,
|
||||
)
|
||||
subprocess.run(["make test"], check=True, shell=True, cwd=REMOTE_ROOT_PATH)
|
||||
|
||||
|
||||
@oldest_v4_app.function(gpu="H100!", image=repo, timeout=90 * 60)
|
||||
def liger_oldest_v4_convergence_tests():
|
||||
import subprocess
|
||||
|
||||
subprocess.run(
|
||||
["uv pip install -e '.[dev]' --system"],
|
||||
check=True,
|
||||
shell=True,
|
||||
cwd=REMOTE_ROOT_PATH,
|
||||
)
|
||||
subprocess.run(
|
||||
[f"uv pip install 'transformers=={OLDEST_SUPPORTED_TRANSFORMERS_V4_VERSION}' --system"],
|
||||
check=True,
|
||||
shell=True,
|
||||
cwd=REMOTE_ROOT_PATH,
|
||||
)
|
||||
subprocess.run(["make test-convergence"], check=True, shell=True, cwd=REMOTE_ROOT_PATH)
|
||||
|
||||
|
||||
latest_v4_app = modal.App("liger_latest_v4_tests", image=image) # 4.57.6
|
||||
|
||||
|
||||
@latest_v4_app.function(gpu="H100!", image=repo, timeout=90 * 60)
|
||||
def liger_latest_v4_correctness_tests():
|
||||
import subprocess
|
||||
|
||||
subprocess.run(
|
||||
["uv pip install -e '.[dev]' --system"],
|
||||
check=True,
|
||||
shell=True,
|
||||
cwd=REMOTE_ROOT_PATH,
|
||||
)
|
||||
subprocess.run(
|
||||
[f"uv pip install 'transformers>={OLDEST_SUPPORTED_TRANSFORMERS_V4_VERSION}, <5.0.0' --system"],
|
||||
check=True,
|
||||
shell=True,
|
||||
cwd=REMOTE_ROOT_PATH,
|
||||
)
|
||||
subprocess.run(["make test"], check=True, shell=True, cwd=REMOTE_ROOT_PATH)
|
||||
|
||||
|
||||
@latest_v4_app.function(gpu="H100!", image=repo, timeout=90 * 60)
|
||||
def liger_latest_v4_convergence_tests():
|
||||
import subprocess
|
||||
|
||||
subprocess.run(
|
||||
["uv pip install -e '.[dev]' --system"],
|
||||
check=True,
|
||||
shell=True,
|
||||
cwd=REMOTE_ROOT_PATH,
|
||||
)
|
||||
subprocess.run(
|
||||
[f"uv pip install 'transformers>={OLDEST_SUPPORTED_TRANSFORMERS_V4_VERSION}, <5.0.0' --system"],
|
||||
check=True,
|
||||
shell=True,
|
||||
cwd=REMOTE_ROOT_PATH,
|
||||
)
|
||||
subprocess.run(["make test-convergence"], check=True, shell=True, cwd=REMOTE_ROOT_PATH)
|
||||
|
||||
@@ -1,35 +0,0 @@
|
||||
from pathlib import Path
|
||||
|
||||
import modal
|
||||
|
||||
ROOT_PATH = Path(__file__).parent.parent.parent
|
||||
REMOTE_ROOT_PATH = "/root/liger-kernel"
|
||||
PYTHON_VERSION = "3.12"
|
||||
|
||||
image = modal.Image.debian_slim(python_version=PYTHON_VERSION).pip_install("uv")
|
||||
|
||||
app = modal.App("liger_tests_bwd", image=image)
|
||||
|
||||
# mount: add local files to the remote container
|
||||
repo = image.add_local_dir(ROOT_PATH, remote_path=REMOTE_ROOT_PATH)
|
||||
|
||||
|
||||
@app.function(gpu="H100!", image=repo, timeout=90 * 60)
|
||||
def liger_bwd_tests():
|
||||
import subprocess
|
||||
|
||||
subprocess.run(
|
||||
["uv pip install -e '.[dev]' --system"],
|
||||
check=True,
|
||||
shell=True,
|
||||
cwd=REMOTE_ROOT_PATH,
|
||||
)
|
||||
# force install transformers==4.52.0
|
||||
subprocess.run(
|
||||
["uv pip install transformers==4.52.0 --system"],
|
||||
check=True,
|
||||
shell=True,
|
||||
cwd=REMOTE_ROOT_PATH,
|
||||
)
|
||||
subprocess.run(["make test"], check=True, shell=True, cwd=REMOTE_ROOT_PATH)
|
||||
subprocess.run(["make test-convergence"], check=True, shell=True, cwd=REMOTE_ROOT_PATH)
|
||||
@@ -33,7 +33,7 @@ def get_optional_dependencies():
|
||||
"""Get optional dependency groups."""
|
||||
return {
|
||||
"dev": [
|
||||
"transformers>=4.52.0, <5.0.0",
|
||||
"transformers>=4.52.0",
|
||||
"matplotlib>=3.7.2",
|
||||
"ruff>=0.12.0",
|
||||
"pytest>=7.1.2",
|
||||
|
||||
@@ -21,6 +21,7 @@ from liger_kernel.transformers.rope import liger_rotary_pos_emb # noqa: F401
|
||||
from liger_kernel.transformers.softmax import LigerSoftmax # noqa: F401
|
||||
from liger_kernel.transformers.sparsemax import LigerSparsemax # noqa: F401
|
||||
from liger_kernel.transformers.swiglu import LigerBlockSparseTop2MLP # noqa: F401
|
||||
from liger_kernel.transformers.swiglu import LigerExperts # noqa: F401
|
||||
from liger_kernel.transformers.swiglu import LigerPhi3SwiGLUMLP # noqa: F401
|
||||
from liger_kernel.transformers.swiglu import LigerQwen3MoeSwiGLUMLP # noqa: F401
|
||||
from liger_kernel.transformers.swiglu import LigerSwiGLUMLP # noqa: F401
|
||||
|
||||
@@ -5,134 +5,13 @@ from typing import Union
|
||||
|
||||
import torch
|
||||
|
||||
from torch.nn import CrossEntropyLoss
|
||||
from transformers.cache_utils import Cache
|
||||
from transformers.modeling_outputs import CausalLMOutputWithPast
|
||||
from transformers.utils.deprecation import deprecate_kwarg
|
||||
|
||||
from liger_kernel.transformers.fused_linear_cross_entropy import LigerFusedLinearCrossEntropyLoss
|
||||
from liger_kernel.transformers.model.loss_utils import LigerForCausalLMLoss
|
||||
from liger_kernel.transformers.model.loss_utils import unpack_cross_entropy_result
|
||||
from liger_kernel.transformers.model.output_classes import LigerCausalLMOutputWithPast
|
||||
|
||||
|
||||
def lce_forward_deprecated(
|
||||
self,
|
||||
input_ids: torch.LongTensor = None,
|
||||
attention_mask: Optional[torch.Tensor] = None,
|
||||
position_ids: Optional[torch.LongTensor] = None,
|
||||
past_key_values: Optional[Union[Cache, List[torch.FloatTensor]]] = None,
|
||||
inputs_embeds: Optional[torch.FloatTensor] = None,
|
||||
labels: Optional[torch.LongTensor] = None,
|
||||
use_cache: Optional[bool] = None,
|
||||
output_attentions: Optional[bool] = None,
|
||||
output_hidden_states: Optional[bool] = None,
|
||||
return_dict: Optional[bool] = None,
|
||||
cache_position: Optional[torch.LongTensor] = None,
|
||||
skip_logits: Optional[bool] = None,
|
||||
) -> Union[Tuple, CausalLMOutputWithPast]:
|
||||
r"""
|
||||
|
||||
copy paste transformers.models.gemma.modeling_gemma causalLM with loss replaced with liger fused cross entropy
|
||||
|
||||
Args:
|
||||
labels (`torch.LongTensor` of shape `(batch_size, sequence_length)`, *optional*):
|
||||
Labels for computing the masked language modeling loss. Indices should either be in `[0, ...,
|
||||
config.vocab_size]` or -100 (see `input_ids` docstring). Tokens with indices set to `-100` are ignored
|
||||
(masked), the loss is only computed for the tokens with labels in `[0, ..., config.vocab_size]`.
|
||||
|
||||
Returns:
|
||||
|
||||
Example:
|
||||
|
||||
```python
|
||||
>>> from transformers import AutoTokenizer, GemmaForCausalLM
|
||||
|
||||
>>> model = GemmaForCausalLM.from_pretrained("google/gemma-7b")
|
||||
>>> tokenizer = AutoTokenizer.from_pretrained("google/gemma-7b")
|
||||
|
||||
>>> prompt = "What is your favorite condiment?"
|
||||
>>> inputs = tokenizer(prompt, return_tensors="pt")
|
||||
|
||||
>>> # Generate
|
||||
>>> generate_ids = model.generate(inputs.input_ids, max_length=30)
|
||||
>>> tokenizer.batch_decode(generate_ids, skip_special_tokens=True, clean_up_tokenization_spaces=False)[0]
|
||||
"What is your favorite condiment?"
|
||||
```"""
|
||||
output_attentions = output_attentions if output_attentions is not None else self.config.output_attentions
|
||||
output_hidden_states = (
|
||||
output_hidden_states if output_hidden_states is not None else self.config.output_hidden_states
|
||||
)
|
||||
return_dict = return_dict if return_dict is not None else self.config.use_return_dict
|
||||
|
||||
# decoder outputs consists of (dec_features, layer_state, dec_hidden, dec_attn)
|
||||
outputs = self.model(
|
||||
input_ids=input_ids,
|
||||
attention_mask=attention_mask,
|
||||
position_ids=position_ids,
|
||||
past_key_values=past_key_values,
|
||||
inputs_embeds=inputs_embeds,
|
||||
use_cache=use_cache,
|
||||
output_attentions=output_attentions,
|
||||
output_hidden_states=output_hidden_states,
|
||||
return_dict=return_dict,
|
||||
cache_position=cache_position,
|
||||
)
|
||||
|
||||
hidden_states = outputs[0]
|
||||
|
||||
loss = None
|
||||
logits = None
|
||||
|
||||
if skip_logits and labels is None:
|
||||
raise ValueError("skip_logits is True, but labels is None")
|
||||
|
||||
if skip_logits is None:
|
||||
# By default, if in training mode, don't materialize logits
|
||||
skip_logits = self.training and labels is not None
|
||||
|
||||
if skip_logits:
|
||||
shift_hidden_states = hidden_states[..., :-1, :].contiguous()
|
||||
shift_labels = labels[..., 1:].contiguous()
|
||||
|
||||
# flatten
|
||||
|
||||
shift_hidden_states = shift_hidden_states.view(-1, self.config.hidden_size)
|
||||
shift_labels = shift_labels.view(-1)
|
||||
|
||||
lce = LigerFusedLinearCrossEntropyLoss()
|
||||
loss = lce(self.lm_head.weight, shift_hidden_states, shift_labels)
|
||||
|
||||
else:
|
||||
logits = self.lm_head(hidden_states)
|
||||
if labels is not None:
|
||||
# Upcast to float if we need to compute the loss to avoid potential precision issues
|
||||
logits = logits.float()
|
||||
# Shift so that tokens < n predict n
|
||||
shift_logits = logits[..., :-1, :].contiguous()
|
||||
shift_labels = labels[..., 1:].contiguous()
|
||||
# Flatten the tokens
|
||||
shift_logits = shift_logits.view(-1, self.config.vocab_size)
|
||||
shift_labels = shift_labels.view(-1)
|
||||
# Ensure tensors are on the same device
|
||||
shift_labels = shift_labels.to(shift_logits.device)
|
||||
loss_fct = CrossEntropyLoss()
|
||||
loss = loss_fct(shift_logits, shift_labels)
|
||||
|
||||
if not return_dict:
|
||||
output = (logits,) + outputs[1:]
|
||||
return (loss,) + output if loss is not None else output
|
||||
|
||||
return CausalLMOutputWithPast(
|
||||
loss=loss,
|
||||
logits=logits,
|
||||
past_key_values=outputs.past_key_values,
|
||||
hidden_states=outputs.hidden_states,
|
||||
attentions=outputs.attentions,
|
||||
)
|
||||
|
||||
|
||||
@deprecate_kwarg("num_logits_to_keep", version="4.50", new_name="logits_to_keep")
|
||||
def lce_forward(
|
||||
self,
|
||||
input_ids: torch.LongTensor = None,
|
||||
|
||||
@@ -6,12 +6,8 @@ from typing import Union
|
||||
|
||||
import torch
|
||||
|
||||
from torch.nn import CrossEntropyLoss
|
||||
from transformers.cache_utils import Cache
|
||||
from transformers.modeling_outputs import CausalLMOutputWithPast
|
||||
from transformers.utils.deprecation import deprecate_kwarg
|
||||
|
||||
from liger_kernel.transformers.fused_linear_cross_entropy import LigerFusedLinearCrossEntropyLoss
|
||||
from liger_kernel.transformers.model.loss_utils import LigerForCausalLMLoss
|
||||
from liger_kernel.transformers.model.loss_utils import unpack_cross_entropy_result
|
||||
from liger_kernel.transformers.model.output_classes import LigerCausalLMOutputWithPast
|
||||
@@ -19,131 +15,6 @@ from liger_kernel.transformers.model.output_classes import LigerCausalLMOutputWi
|
||||
logger = logging.getLogger(__name__)
|
||||
|
||||
|
||||
def lce_forward_deprecated(
|
||||
self,
|
||||
input_ids: torch.LongTensor = None,
|
||||
attention_mask: Optional[torch.Tensor] = None,
|
||||
position_ids: Optional[torch.LongTensor] = None,
|
||||
past_key_values: Optional[Cache] = None,
|
||||
inputs_embeds: Optional[torch.FloatTensor] = None,
|
||||
labels: Optional[torch.LongTensor] = None,
|
||||
use_cache: Optional[bool] = None,
|
||||
output_attentions: Optional[bool] = None,
|
||||
output_hidden_states: Optional[bool] = None,
|
||||
return_dict: Optional[bool] = None,
|
||||
cache_position: Optional[torch.LongTensor] = None,
|
||||
skip_logits: Optional[bool] = None,
|
||||
**kwargs,
|
||||
) -> Union[Tuple, CausalLMOutputWithPast]:
|
||||
r"""
|
||||
Args:
|
||||
labels (`torch.LongTensor` of shape `(batch_size, sequence_length)`, *optional*):
|
||||
Labels for computing the masked language modeling loss. Indices should either be in `[0, ...,
|
||||
config.vocab_size]` or -100 (see `input_ids` docstring). Tokens with indices set to `-100` are ignored
|
||||
(masked), the loss is only computed for the tokens with labels in `[0, ..., config.vocab_size]`.
|
||||
|
||||
Returns:
|
||||
|
||||
Example:
|
||||
|
||||
```python
|
||||
>>> from transformers import AutoTokenizer, GemmaForCausalLM
|
||||
>>> model = GemmaForCausalLM.from_pretrained("google/gemma-2-9b")
|
||||
>>> tokenizer = AutoTokenizer.from_pretrained("google/gemma-2-9b")
|
||||
>>> prompt = "What is your favorite condiment?"
|
||||
>>> inputs = tokenizer(prompt, return_tensors="pt")
|
||||
>>> # Generate
|
||||
>>> generate_ids = model.generate(inputs.input_ids, max_length=30)
|
||||
>>> tokenizer.batch_decode(generate_ids, skip_special_tokens=True, clean_up_tokenization_spaces=False)[0]
|
||||
"What is your favorite condiment?"
|
||||
```"""
|
||||
|
||||
if self.training and self.config._attn_implementation != "eager":
|
||||
logger.warning_once(
|
||||
"It is strongly recommended to train Gemma2 models with the `eager` attention implementation "
|
||||
f"instead of `{self.config._attn_implementation}`. Use `eager` with `AutoModelForCausalLM.from_pretrained('<path-to-checkpoint>', attn_implementation='eager')`."
|
||||
)
|
||||
output_attentions = output_attentions if output_attentions is not None else self.config.output_attentions
|
||||
output_hidden_states = (
|
||||
output_hidden_states if output_hidden_states is not None else self.config.output_hidden_states
|
||||
)
|
||||
return_dict = return_dict if return_dict is not None else self.config.use_return_dict
|
||||
# decoder outputs consists of (dec_features, layer_state, dec_hidden, dec_attn)
|
||||
outputs = self.model(
|
||||
input_ids=input_ids,
|
||||
attention_mask=attention_mask,
|
||||
position_ids=position_ids,
|
||||
past_key_values=past_key_values,
|
||||
inputs_embeds=inputs_embeds,
|
||||
use_cache=use_cache,
|
||||
output_attentions=output_attentions,
|
||||
output_hidden_states=output_hidden_states,
|
||||
return_dict=return_dict,
|
||||
cache_position=cache_position,
|
||||
**kwargs,
|
||||
)
|
||||
|
||||
hidden_states = outputs[0]
|
||||
|
||||
loss = None
|
||||
logits = None
|
||||
|
||||
if skip_logits and labels is None:
|
||||
raise ValueError("skip_logits is True, but labels is None")
|
||||
|
||||
if skip_logits is None:
|
||||
# By default, if in training mode, don't materialize logits
|
||||
skip_logits = self.training and labels is not None
|
||||
|
||||
if skip_logits:
|
||||
shift_hidden_states = hidden_states[..., :-1, :].contiguous()
|
||||
shift_labels = labels[..., 1:].contiguous()
|
||||
|
||||
# flatten
|
||||
|
||||
shift_hidden_states = shift_hidden_states.view(-1, self.config.hidden_size)
|
||||
shift_labels = shift_labels.view(-1)
|
||||
|
||||
lce = LigerFusedLinearCrossEntropyLoss(softcap=self.config.final_logit_softcapping)
|
||||
loss = lce(self.lm_head.weight, shift_hidden_states, shift_labels)
|
||||
|
||||
else:
|
||||
# Only compute necessary logits, and do not upcast them to float if we are not computing the loss
|
||||
logits = self.lm_head(hidden_states)
|
||||
if self.config.final_logit_softcapping is not None:
|
||||
logits = logits / self.config.final_logit_softcapping
|
||||
logits = torch.tanh(logits)
|
||||
logits = logits * self.config.final_logit_softcapping
|
||||
|
||||
loss = None
|
||||
if labels is not None:
|
||||
# Upcast to float if we need to compute the loss to avoid potential precision issues
|
||||
logits = logits.float()
|
||||
# Shift so that tokens < n predict n
|
||||
shift_logits = logits[..., :-1, :].contiguous()
|
||||
shift_labels = labels[..., 1:].contiguous()
|
||||
# Flatten the tokens
|
||||
loss_fct = CrossEntropyLoss()
|
||||
shift_logits = shift_logits.view(-1, self.config.vocab_size)
|
||||
shift_labels = shift_labels.view(-1)
|
||||
# Enable model parallelism
|
||||
shift_labels = shift_labels.to(shift_logits.device)
|
||||
loss = loss_fct(shift_logits, shift_labels)
|
||||
|
||||
if not return_dict:
|
||||
output = (logits,) + outputs[1:]
|
||||
return (loss,) + output if loss is not None else output
|
||||
|
||||
return CausalLMOutputWithPast(
|
||||
loss=loss,
|
||||
logits=logits,
|
||||
past_key_values=outputs.past_key_values,
|
||||
hidden_states=outputs.hidden_states,
|
||||
attentions=outputs.attentions,
|
||||
)
|
||||
|
||||
|
||||
@deprecate_kwarg("num_logits_to_keep", version="4.50", new_name="logits_to_keep")
|
||||
def lce_forward(
|
||||
self,
|
||||
input_ids: torch.LongTensor = None,
|
||||
|
||||
@@ -5,14 +5,11 @@ from typing import Union
|
||||
|
||||
import torch
|
||||
|
||||
from transformers.utils.deprecation import deprecate_kwarg
|
||||
|
||||
from liger_kernel.transformers.model.loss_utils import LigerForCausalLMLoss
|
||||
from liger_kernel.transformers.model.loss_utils import unpack_cross_entropy_result
|
||||
from liger_kernel.transformers.model.output_classes import LigerCausalLMOutputWithPast
|
||||
|
||||
|
||||
@deprecate_kwarg("num_logits_to_keep", version="4.50", new_name="logits_to_keep")
|
||||
def lce_forward(
|
||||
self,
|
||||
input_ids: torch.LongTensor = None,
|
||||
|
||||
@@ -5,14 +5,11 @@ from typing import Union
|
||||
|
||||
import torch
|
||||
|
||||
from transformers.utils.deprecation import deprecate_kwarg
|
||||
|
||||
from liger_kernel.transformers.model.loss_utils import LigerForCausalLMLoss
|
||||
from liger_kernel.transformers.model.loss_utils import unpack_cross_entropy_result
|
||||
from liger_kernel.transformers.model.output_classes import LigerCausalLMOutputWithPast
|
||||
|
||||
|
||||
@deprecate_kwarg("num_logits_to_keep", version="4.50", new_name="logits_to_keep")
|
||||
def lce_forward(
|
||||
self,
|
||||
input_ids: torch.LongTensor = None,
|
||||
|
||||
@@ -4,14 +4,11 @@ from typing import Union
|
||||
|
||||
import torch
|
||||
|
||||
from transformers.utils.deprecation import deprecate_kwarg
|
||||
|
||||
from liger_kernel.transformers.model.loss_utils import LigerForCausalLMLoss
|
||||
from liger_kernel.transformers.model.loss_utils import unpack_cross_entropy_result
|
||||
from liger_kernel.transformers.model.output_classes import LigerGlm4vMoeCausalLMOutputWithPast
|
||||
|
||||
|
||||
@deprecate_kwarg("num_logits_to_keep", version="4.50", new_name="logits_to_keep")
|
||||
def lce_forward(
|
||||
self,
|
||||
input_ids: torch.LongTensor = None,
|
||||
|
||||
@@ -5,15 +5,10 @@ from typing import Tuple
|
||||
from typing import Union
|
||||
|
||||
import torch
|
||||
import torch.nn.functional as F
|
||||
|
||||
from torch.distributed.fsdp import FullyShardedDataParallel
|
||||
from torch.nn import CrossEntropyLoss
|
||||
from transformers.modeling_outputs import CausalLMOutputWithPast
|
||||
from transformers.utils.deprecation import deprecate_kwarg
|
||||
|
||||
from liger_kernel.transformers.fsdp import _FSDPForwardRedirection
|
||||
from liger_kernel.transformers.fused_linear_cross_entropy import LigerFusedLinearCrossEntropyLoss
|
||||
from liger_kernel.transformers.model.loss_utils import LigerForCausalLMLoss
|
||||
from liger_kernel.transformers.model.loss_utils import unpack_cross_entropy_result
|
||||
from liger_kernel.transformers.model.output_classes import LigerCausalLMOutputWithPast
|
||||
@@ -26,128 +21,6 @@ if PEFT_AVAILABLE:
|
||||
from peft.utils.other import ModulesToSaveWrapper
|
||||
|
||||
|
||||
def lce_forward_deprecated(
|
||||
self,
|
||||
input_ids: torch.LongTensor = None,
|
||||
attention_mask: Optional[torch.Tensor] = None,
|
||||
position_ids: Optional[torch.LongTensor] = None,
|
||||
past_key_values: Optional[Union["Cache", List[torch.FloatTensor]]] = None,
|
||||
inputs_embeds: Optional[torch.FloatTensor] = None,
|
||||
labels: Optional[torch.LongTensor] = None,
|
||||
use_cache: Optional[bool] = None,
|
||||
output_attentions: Optional[bool] = None,
|
||||
output_hidden_states: Optional[bool] = None,
|
||||
return_dict: Optional[bool] = None,
|
||||
cache_position: Optional[torch.LongTensor] = None,
|
||||
skip_logits: Optional[bool] = None,
|
||||
) -> Union[Tuple, CausalLMOutputWithPast]:
|
||||
r"""
|
||||
Copy paste llama forward but replace torch cross entropy with liger fused linear cross entropy
|
||||
|
||||
|
||||
Args:
|
||||
labels (`torch.LongTensor` of shape `(batch_size, sequence_length)`, *optional*):
|
||||
Labels for computing the masked language modeling loss. Indices should either be in `[0, ...,
|
||||
config.vocab_size]` or -100 (see `input_ids` docstring). Tokens with indices set to `-100` are ignored
|
||||
(masked), the loss is only computed for the tokens with labels in `[0, ..., config.vocab_size]`.
|
||||
|
||||
Returns:
|
||||
|
||||
Example:
|
||||
|
||||
```python
|
||||
>>> from transformers import AutoTokenizer, LlamaForCausalLM
|
||||
|
||||
>>> model = LlamaForCausalLM.from_pretrained("meta-llama/Llama-2-7b-hf")
|
||||
>>> tokenizer = AutoTokenizer.from_pretrained("meta-llama/Llama-2-7b-hf")
|
||||
|
||||
>>> prompt = "Hey, are you conscious? Can you talk to me?"
|
||||
>>> inputs = tokenizer(prompt, return_tensors="pt")
|
||||
|
||||
>>> # Generate
|
||||
>>> generate_ids = model.generate(inputs.input_ids, max_length=30)
|
||||
>>> tokenizer.batch_decode(generate_ids, skip_special_tokens=True, clean_up_tokenization_spaces=False)[0]
|
||||
"Hey, are you conscious? Can you talk to me?\nI'm not conscious, but I can talk to you."
|
||||
```"""
|
||||
output_attentions = output_attentions if output_attentions is not None else self.config.output_attentions
|
||||
output_hidden_states = (
|
||||
output_hidden_states if output_hidden_states is not None else self.config.output_hidden_states
|
||||
)
|
||||
return_dict = return_dict if return_dict is not None else self.config.use_return_dict
|
||||
|
||||
# decoder outputs consists of (dec_features, layer_state, dec_hidden, dec_attn)
|
||||
outputs = self.model(
|
||||
input_ids=input_ids,
|
||||
attention_mask=attention_mask,
|
||||
position_ids=position_ids,
|
||||
past_key_values=past_key_values,
|
||||
inputs_embeds=inputs_embeds,
|
||||
use_cache=use_cache,
|
||||
output_attentions=output_attentions,
|
||||
output_hidden_states=output_hidden_states,
|
||||
return_dict=return_dict,
|
||||
cache_position=cache_position,
|
||||
)
|
||||
|
||||
hidden_states = outputs[0]
|
||||
|
||||
loss = None
|
||||
logits = None
|
||||
|
||||
# if in training mode, don't materialize logits
|
||||
if skip_logits and labels is None:
|
||||
raise ValueError("skip_logits is True, but labels is None")
|
||||
|
||||
if skip_logits is None:
|
||||
# By default, if in training mode, don't materialize logits
|
||||
skip_logits = self.training and labels is not None
|
||||
|
||||
if skip_logits:
|
||||
shift_hidden_states = hidden_states[..., :-1, :].contiguous()
|
||||
shift_labels = labels[..., 1:].contiguous()
|
||||
|
||||
# flatten tokens
|
||||
shift_hidden_states = shift_hidden_states.view(-1, self.config.hidden_size)
|
||||
shift_labels = shift_labels.view(-1)
|
||||
|
||||
lce = LigerFusedLinearCrossEntropyLoss()
|
||||
loss = lce(self.lm_head.weight, shift_hidden_states, shift_labels)
|
||||
|
||||
else:
|
||||
if self.config.pretraining_tp > 1:
|
||||
lm_head_slices = self.lm_head.weight.split(self.vocab_size // self.config.pretraining_tp, dim=0)
|
||||
logits = [F.linear(hidden_states, lm_head_slices[i]) for i in range(self.config.pretraining_tp)]
|
||||
logits = torch.cat(logits, dim=-1)
|
||||
else:
|
||||
logits = self.lm_head(hidden_states)
|
||||
if labels is not None:
|
||||
# Upcast to float if we need to compute the loss to avoid potential precision issues
|
||||
logits = logits.float()
|
||||
# Shift so that tokens < n predict n
|
||||
shift_logits = logits[..., :-1, :].contiguous()
|
||||
shift_labels = labels[..., 1:].contiguous()
|
||||
# Flatten the tokens
|
||||
loss_fct = CrossEntropyLoss()
|
||||
shift_logits = shift_logits.view(-1, self.config.vocab_size)
|
||||
shift_labels = shift_labels.view(-1)
|
||||
# Enable model parallelism
|
||||
shift_labels = shift_labels.to(shift_logits.device)
|
||||
loss = loss_fct(shift_logits, shift_labels)
|
||||
|
||||
if not return_dict:
|
||||
output = (logits,) + outputs[1:]
|
||||
return (loss,) + output if loss is not None else output
|
||||
|
||||
return CausalLMOutputWithPast(
|
||||
loss=loss,
|
||||
logits=logits,
|
||||
past_key_values=outputs.past_key_values,
|
||||
hidden_states=outputs.hidden_states,
|
||||
attentions=outputs.attentions,
|
||||
)
|
||||
|
||||
|
||||
@deprecate_kwarg("num_logits_to_keep", version="4.50", new_name="logits_to_keep")
|
||||
def lce_forward(
|
||||
self,
|
||||
input_ids: torch.LongTensor = None,
|
||||
|
||||
@@ -5,198 +5,11 @@ from typing import Union
|
||||
|
||||
import torch
|
||||
|
||||
from torch.nn import CrossEntropyLoss
|
||||
from transformers.models.llava.modeling_llava import LlavaCausalLMOutputWithPast
|
||||
from transformers.utils import is_torchdynamo_compiling
|
||||
|
||||
from liger_kernel.transformers.fused_linear_cross_entropy import LigerFusedLinearCrossEntropyLoss
|
||||
from liger_kernel.transformers.model.loss_utils import LigerForCausalLMLoss
|
||||
from liger_kernel.transformers.model.loss_utils import unpack_cross_entropy_result
|
||||
from liger_kernel.transformers.model.output_classes import LigerLlavaCausalLMOutputWithPast
|
||||
|
||||
|
||||
def lce_forward_deprecated(
|
||||
self,
|
||||
input_ids: torch.LongTensor = None,
|
||||
pixel_values: torch.FloatTensor = None,
|
||||
attention_mask: Optional[torch.Tensor] = None,
|
||||
position_ids: Optional[torch.LongTensor] = None,
|
||||
past_key_values: Optional[List[torch.FloatTensor]] = None,
|
||||
inputs_embeds: Optional[torch.FloatTensor] = None,
|
||||
vision_feature_layer: Optional[int] = None,
|
||||
vision_feature_select_strategy: Optional[str] = None,
|
||||
labels: Optional[torch.LongTensor] = None,
|
||||
use_cache: Optional[bool] = None,
|
||||
output_attentions: Optional[bool] = None,
|
||||
output_hidden_states: Optional[bool] = None,
|
||||
return_dict: Optional[bool] = None,
|
||||
cache_position: Optional[torch.LongTensor] = None,
|
||||
logits_to_keep: Union[int, torch.Tensor] = 0,
|
||||
image_sizes: torch.Tensor = None,
|
||||
skip_logits: Optional[bool] = None,
|
||||
**lm_kwargs,
|
||||
) -> Union[Tuple, LlavaCausalLMOutputWithPast]:
|
||||
r"""
|
||||
Args:
|
||||
labels (`torch.LongTensor` of shape `(batch_size, sequence_length)`, *optional*):
|
||||
Labels for computing the masked language modeling loss. Indices should either be in `[0, ...,
|
||||
config.vocab_size]` or -100 (see `input_ids` docstring). Tokens with indices set to `-100` are ignored
|
||||
(masked), the loss is only computed for the tokens with labels in `[0, ..., config.vocab_size]`.
|
||||
|
||||
logits_to_keep (`int` or `torch.Tensor`, *optional*):
|
||||
If an `int`, compute logits for the last `logits_to_keep` tokens. If `0`, calculate logits for all
|
||||
`input_ids` (special case). Only last token logits are needed for generation, and calculating them only for that
|
||||
token can save memory, which becomes pretty significant for long sequences or large vocabulary size.
|
||||
If a `torch.Tensor`, must be 1D corresponding to the indices to keep in the sequence length dimension.
|
||||
This is useful when using packed tensor format (single dimension for batch and sequence length).
|
||||
|
||||
|
||||
Returns:
|
||||
|
||||
Example:
|
||||
|
||||
```python
|
||||
>>> from PIL import Image
|
||||
>>> import requests
|
||||
>>> from transformers import AutoProcessor, LlavaForConditionalGeneration
|
||||
|
||||
>>> model = LlavaForConditionalGeneration.from_pretrained("llava-hf/llava-1.5-7b-hf")
|
||||
>>> processor = AutoProcessor.from_pretrained("llava-hf/llava-1.5-7b-hf")
|
||||
|
||||
>>> prompt = "USER: <image>\nWhat's the content of the image? ASSISTANT:"
|
||||
>>> url = "https://www.ilankelman.org/stopsigns/australia.jpg"
|
||||
>>> image = Image.open(requests.get(url, stream=True).raw)
|
||||
|
||||
>>> inputs = processor(images=image, text=prompt, return_tensors="pt")
|
||||
|
||||
>>> # Generate
|
||||
>>> generate_ids = model.generate(**inputs, max_new_tokens=15)
|
||||
>>> processor.batch_decode(generate_ids, skip_special_tokens=True, clean_up_tokenization_spaces=False)[0]
|
||||
"USER: \nWhat's the content of the image? ASSISTANT: The image features a busy city street with a stop sign prominently displayed"
|
||||
```"""
|
||||
output_attentions = output_attentions if output_attentions is not None else self.config.output_attentions
|
||||
output_hidden_states = (
|
||||
output_hidden_states if output_hidden_states is not None else self.config.output_hidden_states
|
||||
)
|
||||
return_dict = return_dict if return_dict is not None else self.config.use_return_dict
|
||||
vision_feature_layer = (
|
||||
vision_feature_layer if vision_feature_layer is not None else self.config.vision_feature_layer
|
||||
)
|
||||
vision_feature_select_strategy = (
|
||||
vision_feature_select_strategy
|
||||
if vision_feature_select_strategy is not None
|
||||
else self.config.vision_feature_select_strategy
|
||||
)
|
||||
|
||||
if (input_ids is None) ^ (inputs_embeds is not None):
|
||||
raise ValueError("You must specify exactly one of input_ids or inputs_embeds")
|
||||
|
||||
if pixel_values is not None and inputs_embeds is not None:
|
||||
raise ValueError(
|
||||
"You cannot specify both pixel_values and inputs_embeds at the same time, and must specify either one"
|
||||
)
|
||||
|
||||
if inputs_embeds is None:
|
||||
inputs_embeds = self.get_input_embeddings()(input_ids)
|
||||
|
||||
if pixel_values is not None:
|
||||
image_features = self.get_image_features(
|
||||
pixel_values=pixel_values,
|
||||
vision_feature_layer=vision_feature_layer,
|
||||
vision_feature_select_strategy=vision_feature_select_strategy,
|
||||
image_sizes=image_sizes,
|
||||
)
|
||||
|
||||
special_image_mask = (input_ids == self.config.image_token_index).unsqueeze(-1)
|
||||
special_image_mask = special_image_mask.expand_as(inputs_embeds).to(inputs_embeds.device)
|
||||
if not is_torchdynamo_compiling() and inputs_embeds[special_image_mask].numel() != image_features.numel():
|
||||
n_image_tokens = (input_ids == self.config.image_token_index).sum()
|
||||
n_image_features = image_features.shape[0] * image_features.shape[1]
|
||||
raise ValueError(
|
||||
f"Image features and image tokens do not match: tokens: {n_image_tokens}, features {n_image_features}"
|
||||
)
|
||||
image_features = image_features.to(inputs_embeds.device, inputs_embeds.dtype)
|
||||
inputs_embeds = inputs_embeds.masked_scatter(special_image_mask, image_features)
|
||||
|
||||
outputs = self.language_model.model(
|
||||
attention_mask=attention_mask,
|
||||
position_ids=position_ids,
|
||||
past_key_values=past_key_values,
|
||||
inputs_embeds=inputs_embeds,
|
||||
use_cache=use_cache,
|
||||
output_attentions=output_attentions,
|
||||
output_hidden_states=output_hidden_states,
|
||||
return_dict=return_dict,
|
||||
cache_position=cache_position,
|
||||
logits_to_keep=logits_to_keep,
|
||||
**lm_kwargs,
|
||||
)
|
||||
hidden_states = outputs[0]
|
||||
|
||||
loss = None
|
||||
logits = None
|
||||
|
||||
# Overwrite skip_logits, since llava never materializes logits
|
||||
skip_logits = labels is not None
|
||||
|
||||
if skip_logits:
|
||||
# Shift so that tokens < n predict n
|
||||
if attention_mask is not None:
|
||||
# we use the input attention mask to shift the logits and labels, because it is 2D.
|
||||
# we also crop attn mask in case it is longer, which happens in PrefixTuning with peft
|
||||
shift_attention_mask = attention_mask[:, -(hidden_states.shape[1] - 1) :].to(hidden_states.device)
|
||||
shift_hidden_states = hidden_states[..., :-1, :][
|
||||
shift_attention_mask.to(hidden_states.device) != 0
|
||||
].contiguous()
|
||||
shift_labels = labels[..., 1:][shift_attention_mask.to(labels.device) != 0].contiguous()
|
||||
else:
|
||||
shift_hidden_states = hidden_states[..., :-1, :].contiguous()
|
||||
shift_labels = labels[..., 1:].contiguous()
|
||||
|
||||
lce = LigerFusedLinearCrossEntropyLoss()
|
||||
loss = lce(
|
||||
self.language_model.lm_head.weight,
|
||||
shift_hidden_states.view(-1, shift_hidden_states.size(-1)),
|
||||
shift_labels.view(-1).to(shift_hidden_states.device),
|
||||
)
|
||||
else:
|
||||
logits = self.language_model.lm_head(hidden_states)
|
||||
if labels is not None:
|
||||
# Upcast to float if we need to compute the loss to avoid potential precision issues
|
||||
logits = logits.float()
|
||||
shift_logits = logits[..., :-1, :]
|
||||
shift_labels = labels[..., 1:]
|
||||
if attention_mask is not None:
|
||||
# we use the input attention mask to shift the logits and labels, because it is 2D.
|
||||
# we also crop attn mask in case it is longer, which happens in PrefixTuning with peft
|
||||
shift_attention_mask = attention_mask[:, -shift_logits.shape[1] :].to(logits.device)
|
||||
shift_logits = shift_logits[shift_attention_mask.to(logits.device) != 0].contiguous()
|
||||
shift_labels = shift_labels[shift_attention_mask.to(shift_labels.device) != 0].contiguous()
|
||||
else:
|
||||
shift_logits = shift_logits.contiguous()
|
||||
shift_labels = shift_labels.contiguous()
|
||||
# Flatten the tokens
|
||||
loss_fct = CrossEntropyLoss()
|
||||
|
||||
flat_logits = shift_logits.view(-1, self.config.text_config.vocab_size)
|
||||
flat_labels = shift_labels.view(-1).to(shift_logits.device)
|
||||
loss = loss_fct(flat_logits, flat_labels)
|
||||
|
||||
if not return_dict:
|
||||
# NOTE: This part has not been tested.
|
||||
output = outputs[1:]
|
||||
return (loss,) + output if loss is not None else output
|
||||
|
||||
return LlavaCausalLMOutputWithPast(
|
||||
loss=loss,
|
||||
logits=logits,
|
||||
past_key_values=outputs.past_key_values,
|
||||
hidden_states=outputs.hidden_states,
|
||||
attentions=outputs.attentions,
|
||||
image_hidden_states=image_features if pixel_values is not None else None,
|
||||
)
|
||||
|
||||
|
||||
def lce_forward(
|
||||
self,
|
||||
input_ids: torch.LongTensor = None,
|
||||
|
||||
@@ -6,14 +6,12 @@ from typing import Union
|
||||
import torch
|
||||
|
||||
from transformers.cache_utils import Cache
|
||||
from transformers.utils.deprecation import deprecate_kwarg
|
||||
|
||||
from liger_kernel.transformers.model.loss_utils import LigerForCausalLMLoss
|
||||
from liger_kernel.transformers.model.loss_utils import unpack_cross_entropy_result
|
||||
from liger_kernel.transformers.model.output_classes import LigerCausalLMOutputWithPast
|
||||
|
||||
|
||||
@deprecate_kwarg("num_logits_to_keep", version="4.50", new_name="logits_to_keep")
|
||||
def lce_forward(
|
||||
self,
|
||||
input_ids: torch.LongTensor = None,
|
||||
|
||||
@@ -5,143 +5,13 @@ from typing import Union
|
||||
|
||||
import torch
|
||||
|
||||
from torch.nn import CrossEntropyLoss
|
||||
from transformers.modeling_outputs import MoeCausalLMOutputWithPast
|
||||
from transformers.models.mixtral.modeling_mixtral import load_balancing_loss_func
|
||||
from transformers.utils.deprecation import deprecate_kwarg
|
||||
|
||||
from liger_kernel.transformers.fused_linear_cross_entropy import LigerFusedLinearCrossEntropyLoss
|
||||
from liger_kernel.transformers.model.loss_utils import LigerForCausalLMLoss
|
||||
from liger_kernel.transformers.model.loss_utils import unpack_cross_entropy_result
|
||||
from liger_kernel.transformers.model.output_classes import LigerMoeCausalLMOutputWithPast
|
||||
|
||||
|
||||
def lce_forward_deprecated(
|
||||
self,
|
||||
input_ids: torch.LongTensor = None,
|
||||
attention_mask: Optional[torch.Tensor] = None,
|
||||
position_ids: Optional[torch.LongTensor] = None,
|
||||
past_key_values: Optional[List[torch.FloatTensor]] = None,
|
||||
inputs_embeds: Optional[torch.FloatTensor] = None,
|
||||
labels: Optional[torch.LongTensor] = None,
|
||||
use_cache: Optional[bool] = None,
|
||||
output_attentions: Optional[bool] = None,
|
||||
output_hidden_states: Optional[bool] = None,
|
||||
output_router_logits: Optional[bool] = None,
|
||||
return_dict: Optional[bool] = None,
|
||||
cache_position: Optional[torch.LongTensor] = None,
|
||||
) -> Union[Tuple, MoeCausalLMOutputWithPast]:
|
||||
r"""
|
||||
Copy paste Mixtral's forward from transformers v4.44.2 but replace torch cross entropy with liger fused linear cross entropy
|
||||
|
||||
|
||||
Args:
|
||||
labels (`torch.LongTensor` of shape `(batch_size, sequence_length)`, *optional*):
|
||||
Labels for computing the masked language modeling loss. Indices should either be in `[0, ...,
|
||||
config.vocab_size]` or -100 (see `input_ids` docstring). Tokens with indices set to `-100` are ignored
|
||||
(masked), the loss is only computed for the tokens with labels in `[0, ..., config.vocab_size]`.
|
||||
|
||||
Returns:
|
||||
|
||||
Example:
|
||||
|
||||
```python
|
||||
>>> from transformers import AutoTokenizer, MixtralForCausalLM
|
||||
|
||||
>>> model = MixtralForCausalLM.from_pretrained("mistralai/Mixtral-8x7B-v0.1")
|
||||
>>> tokenizer = AutoTokenizer.from_pretrained("mistralai/Mixtral-8x7B-v0.1")
|
||||
|
||||
>>> prompt = "Hey, are you conscious? Can you talk to me?"
|
||||
>>> inputs = tokenizer(prompt, return_tensors="pt")
|
||||
|
||||
>>> # Generate
|
||||
>>> generate_ids = model.generate(inputs.input_ids, max_length=30)
|
||||
>>> tokenizer.batch_decode(generate_ids, skip_special_tokens=True, clean_up_tokenization_spaces=False)[0]
|
||||
"Hey, are you conscious? Can you talk to me?\nI'm not conscious, but I can talk to you."
|
||||
```"""
|
||||
|
||||
output_attentions = output_attentions if output_attentions is not None else self.config.output_attentions
|
||||
output_router_logits = (
|
||||
output_router_logits if output_router_logits is not None else self.config.output_router_logits
|
||||
)
|
||||
|
||||
output_hidden_states = (
|
||||
output_hidden_states if output_hidden_states is not None else self.config.output_hidden_states
|
||||
)
|
||||
return_dict = return_dict if return_dict is not None else self.config.use_return_dict
|
||||
|
||||
# decoder outputs consists of (dec_features, layer_state, dec_hidden, dec_attn)
|
||||
outputs = self.model(
|
||||
input_ids=input_ids,
|
||||
attention_mask=attention_mask,
|
||||
position_ids=position_ids,
|
||||
past_key_values=past_key_values,
|
||||
inputs_embeds=inputs_embeds,
|
||||
use_cache=use_cache,
|
||||
output_attentions=output_attentions,
|
||||
output_hidden_states=output_hidden_states,
|
||||
output_router_logits=output_router_logits,
|
||||
return_dict=return_dict,
|
||||
cache_position=cache_position,
|
||||
)
|
||||
|
||||
hidden_states = outputs[0]
|
||||
logits = self.lm_head(hidden_states)
|
||||
|
||||
loss = None
|
||||
if self.training and (labels is not None):
|
||||
shift_hidden_states = hidden_states[..., :-1, :].contiguous()
|
||||
shift_labels = labels[..., 1:].contiguous()
|
||||
# Flatten the tokens
|
||||
shift_hidden_states = shift_hidden_states.view(-1, self.config.hidden_size)
|
||||
shift_labels = shift_labels.view(-1)
|
||||
|
||||
lce = LigerFusedLinearCrossEntropyLoss()
|
||||
loss = lce(self.lm_head.weight, shift_hidden_states, shift_labels)
|
||||
elif labels is not None:
|
||||
# Upcast to float if we need to compute the loss to avoid potential precision issues
|
||||
logits = logits.float()
|
||||
# Shift so that tokens < n predict n
|
||||
shift_logits = logits[..., :-1, :].contiguous()
|
||||
shift_labels = labels[..., 1:].contiguous()
|
||||
# Flatten the tokens
|
||||
shift_logits = shift_logits.view(-1, self.config.vocab_size)
|
||||
shift_labels = shift_labels.view(-1)
|
||||
# Enable model parallelism
|
||||
shift_labels = shift_labels.to(shift_logits.device)
|
||||
|
||||
loss_fct = CrossEntropyLoss()
|
||||
loss = loss_fct(logits.weight, shift_labels)
|
||||
|
||||
aux_loss = None
|
||||
if output_router_logits:
|
||||
aux_loss = load_balancing_loss_func(
|
||||
outputs.router_logits if return_dict else outputs[-1],
|
||||
self.num_experts,
|
||||
self.num_experts_per_tok,
|
||||
attention_mask,
|
||||
)
|
||||
if labels is not None:
|
||||
loss += self.router_aux_loss_coef * aux_loss.to(loss.device) # make sure to reside in the same device
|
||||
|
||||
if not return_dict:
|
||||
output = (logits,) + outputs[1:]
|
||||
if output_router_logits:
|
||||
output = (aux_loss,) + output
|
||||
return (loss,) + output if loss is not None else output
|
||||
|
||||
return MoeCausalLMOutputWithPast(
|
||||
loss=loss,
|
||||
aux_loss=aux_loss,
|
||||
logits=logits,
|
||||
past_key_values=outputs.past_key_values,
|
||||
hidden_states=outputs.hidden_states,
|
||||
attentions=outputs.attentions,
|
||||
router_logits=outputs.router_logits,
|
||||
)
|
||||
|
||||
|
||||
@deprecate_kwarg("num_logits_to_keep", version="4.50", new_name="logits_to_keep")
|
||||
# Ignore copy
|
||||
def lce_forward(
|
||||
self,
|
||||
|
||||
@@ -5,133 +5,13 @@ from typing import Union
|
||||
|
||||
import torch
|
||||
|
||||
from torch.nn import CrossEntropyLoss
|
||||
from transformers.cache_utils import Cache
|
||||
from transformers.modeling_outputs import CausalLMOutputWithPast
|
||||
from transformers.utils.deprecation import deprecate_kwarg
|
||||
|
||||
from liger_kernel.transformers.fused_linear_cross_entropy import LigerFusedLinearCrossEntropyLoss
|
||||
from liger_kernel.transformers.model.loss_utils import LigerForCausalLMLoss
|
||||
from liger_kernel.transformers.model.loss_utils import unpack_cross_entropy_result
|
||||
from liger_kernel.transformers.model.output_classes import LigerCausalLMOutputWithPast
|
||||
|
||||
|
||||
def lce_forward_deprecated(
|
||||
self,
|
||||
input_ids: torch.LongTensor = None,
|
||||
attention_mask: Optional[torch.Tensor] = None,
|
||||
position_ids: Optional[torch.LongTensor] = None,
|
||||
cross_attention_states: Optional[torch.LongTensor] = None,
|
||||
cross_attention_mask: Optional[torch.LongTensor] = None,
|
||||
full_text_row_masked_out_mask: Optional[Tuple[torch.Tensor, torch.Tensor]] = None,
|
||||
past_key_values: Optional[Union[Cache, List[torch.FloatTensor]]] = None,
|
||||
inputs_embeds: Optional[torch.FloatTensor] = None,
|
||||
labels: Optional[torch.LongTensor] = None,
|
||||
use_cache: Optional[bool] = None,
|
||||
output_attentions: Optional[bool] = None,
|
||||
output_hidden_states: Optional[bool] = None,
|
||||
return_dict: Optional[bool] = None,
|
||||
cache_position: Optional[torch.LongTensor] = None,
|
||||
num_logits_to_keep: int = 0,
|
||||
) -> Union[Tuple, CausalLMOutputWithPast]:
|
||||
r"""
|
||||
Copy paste mllama forward but replace torch cross entropy with liger fused linear cross entropy
|
||||
|
||||
|
||||
Args:
|
||||
labels (`torch.LongTensor` of shape `(batch_size, sequence_length)`, *optional*):
|
||||
Labels for computing the masked language modeling loss. Indices should either be in `[0, ...,
|
||||
config.vocab_size]` or -100 (see `input_ids` docstring). Tokens with indices set to `-100` are ignored
|
||||
(masked), the loss is only computed for the tokens with labels in `[0, ..., config.vocab_size]`.
|
||||
num_logits_to_keep (`int`, *optional*):
|
||||
Calculate logits for the last `num_logits_to_keep` tokens. If `0`, calculate logits for all
|
||||
`input_ids` (special case). Only last token logits are needed for generation, and calculating them only for that
|
||||
token can save memory, which becomes pretty significant for long sequences or large vocabulary size.
|
||||
Returns:
|
||||
Example:
|
||||
```python
|
||||
>>> from transformers import AutoTokenizer, MllamaForCausalLM
|
||||
>>> model = MllamaForCausalLM.from_pretrained("Llama-3.2-11B-Vision")
|
||||
>>> tokenizer = AutoTokenizer.from_pretrained("Llama-3.2-11B-Vision")
|
||||
>>> prompt = "If I had to write a haiku, it would be:"
|
||||
>>> inputs = tokenizer(prompt, return_tensors="pt")
|
||||
>>> # Generate
|
||||
>>> generate_ids = model.generate(inputs.input_ids, max_length=40, do_sample=True, temperature=0.6)
|
||||
>>> result = tokenizer.batch_decode(generate_ids, skip_special_tokens=True, clean_up_tokenization_spaces=False)[0]
|
||||
>>> print(result)
|
||||
If I had to write a haiku, it would be: "Snowflakes gently fall" - simple, yet peaceful.
|
||||
I love the idea of snowflakes gently falling, each one
|
||||
```
|
||||
"""
|
||||
output_attentions = output_attentions if output_attentions is not None else self.config.output_attentions
|
||||
output_hidden_states = (
|
||||
output_hidden_states if output_hidden_states is not None else self.config.output_hidden_states
|
||||
)
|
||||
return_dict = return_dict if return_dict is not None else self.config.use_return_dict
|
||||
|
||||
# decoder outputs consists of (dec_features, layer_state, dec_hidden, dec_attn)
|
||||
outputs = self.model(
|
||||
input_ids=input_ids,
|
||||
cross_attention_states=cross_attention_states,
|
||||
attention_mask=attention_mask,
|
||||
position_ids=position_ids,
|
||||
cross_attention_mask=cross_attention_mask,
|
||||
full_text_row_masked_out_mask=full_text_row_masked_out_mask,
|
||||
past_key_values=past_key_values,
|
||||
inputs_embeds=inputs_embeds,
|
||||
use_cache=use_cache,
|
||||
output_attentions=output_attentions,
|
||||
output_hidden_states=output_hidden_states,
|
||||
return_dict=return_dict,
|
||||
cache_position=cache_position,
|
||||
)
|
||||
|
||||
hidden_states = outputs[0]
|
||||
|
||||
loss = None
|
||||
logits = None
|
||||
|
||||
if self.training and (labels is not None):
|
||||
kept_hidden_states = hidden_states[:, -num_logits_to_keep:, :]
|
||||
|
||||
shift_hidden_states = kept_hidden_states[..., :-1, :].contiguous()
|
||||
shift_labels = labels[..., 1:].contiguous()
|
||||
|
||||
# flatten tokens
|
||||
shift_hidden_states = shift_hidden_states.view(-1, self.config.hidden_size)
|
||||
shift_labels = shift_labels.view(-1)
|
||||
|
||||
lce = LigerFusedLinearCrossEntropyLoss()
|
||||
loss = lce(self.lm_head.weight, shift_hidden_states, shift_labels)
|
||||
|
||||
else:
|
||||
logits = self.lm_head(hidden_states[:, -num_logits_to_keep:, :]).float()
|
||||
if labels is not None:
|
||||
# Shift so that tokens < n predict n
|
||||
shift_logits = logits[..., :-1, :].contiguous()
|
||||
shift_labels = labels[..., 1:].contiguous()
|
||||
# Flatten the tokens
|
||||
loss_fct = CrossEntropyLoss()
|
||||
shift_logits = shift_logits.view(-1, self.config.vocab_size)
|
||||
shift_labels = shift_labels.view(-1)
|
||||
# Enable model parallelism
|
||||
shift_labels = shift_labels.to(shift_logits.device)
|
||||
loss = loss_fct(shift_logits, shift_labels)
|
||||
|
||||
if not return_dict:
|
||||
output = (logits,) + outputs[1:]
|
||||
return (loss,) + output if loss is not None else output
|
||||
|
||||
return CausalLMOutputWithPast(
|
||||
loss=loss,
|
||||
logits=logits,
|
||||
past_key_values=outputs.past_key_values,
|
||||
hidden_states=outputs.hidden_states,
|
||||
attentions=outputs.attentions,
|
||||
)
|
||||
|
||||
|
||||
@deprecate_kwarg("num_logits_to_keep", version="4.50", new_name="logits_to_keep")
|
||||
def lce_forward(
|
||||
self,
|
||||
input_ids: torch.LongTensor = None,
|
||||
@@ -192,9 +72,6 @@ def lce_forward(
|
||||
output_hidden_states if output_hidden_states is not None else self.config.output_hidden_states
|
||||
)
|
||||
return_dict = return_dict if return_dict is not None else self.config.use_return_dict
|
||||
# Filter out accum_dtype from kwargs for model call as MllamaTextModel doesn't accept it in transformers 4.49.0
|
||||
# but preserve it for loss function calls
|
||||
model_kwargs = {k: v for k, v in kwargs.items() if k != "accum_dtype"}
|
||||
# decoder outputs consists of (dec_features, layer_state, dec_hidden, dec_attn)
|
||||
outputs = self.model(
|
||||
input_ids=input_ids,
|
||||
@@ -210,7 +87,7 @@ def lce_forward(
|
||||
output_hidden_states=output_hidden_states,
|
||||
return_dict=return_dict,
|
||||
cache_position=cache_position,
|
||||
**model_kwargs,
|
||||
**kwargs,
|
||||
)
|
||||
|
||||
hidden_states = outputs[0]
|
||||
|
||||
@@ -5,14 +5,11 @@ from typing import Union
|
||||
|
||||
import torch
|
||||
|
||||
from transformers.utils.deprecation import deprecate_kwarg
|
||||
|
||||
from liger_kernel.transformers.model.loss_utils import LigerForCausalLMLoss
|
||||
from liger_kernel.transformers.model.loss_utils import unpack_cross_entropy_result
|
||||
from liger_kernel.transformers.model.output_classes import LigerCausalLMOutputWithPast
|
||||
|
||||
|
||||
@deprecate_kwarg("num_logits_to_keep", version="4.50", new_name="logits_to_keep")
|
||||
def lce_forward(
|
||||
self,
|
||||
input_ids: torch.LongTensor = None,
|
||||
|
||||
@@ -6,14 +6,12 @@ from typing import Union
|
||||
import torch
|
||||
|
||||
from transformers.modeling_outputs import BaseModelOutputWithPast
|
||||
from transformers.utils.deprecation import deprecate_kwarg
|
||||
|
||||
from liger_kernel.transformers.model.loss_utils import LigerForCausalLMLoss
|
||||
from liger_kernel.transformers.model.loss_utils import unpack_cross_entropy_result
|
||||
from liger_kernel.transformers.model.output_classes import LigerCausalLMOutputWithPast
|
||||
|
||||
|
||||
@deprecate_kwarg("num_logits_to_keep", version="4.50", new_name="logits_to_keep")
|
||||
def lce_forward(
|
||||
self,
|
||||
input_ids: torch.LongTensor = None,
|
||||
|
||||
@@ -7,12 +7,9 @@ import torch
|
||||
|
||||
from torch.nn import CrossEntropyLoss
|
||||
from transformers.cache_utils import Cache
|
||||
from transformers.models.paligemma.modeling_paligemma import PaliGemmaCausalLMOutputWithPast
|
||||
from transformers.utils import is_torchdynamo_compiling
|
||||
from transformers.utils import logging
|
||||
from transformers.utils.deprecation import deprecate_kwarg
|
||||
|
||||
from liger_kernel.transformers.fused_linear_cross_entropy import LigerFusedLinearCrossEntropyLoss
|
||||
from liger_kernel.transformers.model.loss_utils import LigerForCausalLMLoss
|
||||
from liger_kernel.transformers.model.loss_utils import unpack_cross_entropy_result
|
||||
from liger_kernel.transformers.model.output_classes import LigerPaliGemmaCausalLMOutputWithPast
|
||||
@@ -20,189 +17,6 @@ from liger_kernel.transformers.model.output_classes import LigerPaliGemmaCausalL
|
||||
logger = logging.get_logger(__name__)
|
||||
|
||||
|
||||
def lce_forward_deprecated(
|
||||
self,
|
||||
input_ids: torch.LongTensor = None,
|
||||
pixel_values: torch.FloatTensor = None,
|
||||
attention_mask: Optional[torch.Tensor] = None,
|
||||
position_ids: Optional[torch.LongTensor] = None,
|
||||
past_key_values: Optional[Union[List[torch.FloatTensor], Cache]] = None,
|
||||
token_type_ids: Optional[torch.LongTensor] = None,
|
||||
cache_position: Optional[torch.LongTensor] = None,
|
||||
inputs_embeds: Optional[torch.FloatTensor] = None,
|
||||
labels: Optional[torch.LongTensor] = None,
|
||||
use_cache: Optional[bool] = None,
|
||||
output_attentions: Optional[bool] = None,
|
||||
output_hidden_states: Optional[bool] = None,
|
||||
return_dict: Optional[bool] = None,
|
||||
) -> Union[Tuple, PaliGemmaCausalLMOutputWithPast]:
|
||||
r"""
|
||||
Args:
|
||||
labels (`torch.LongTensor` of shape `(batch_size, sequence_length)`, *optional*):
|
||||
Labels for computing the masked language modeling loss. Indices should either be in `[0, ...,
|
||||
config.vocab_size]` or -100 (see `input_ids` docstring). Tokens with indices set to `-100` are ignored
|
||||
(masked), the loss is only computed for the tokens with labels in `[0, ..., config.vocab_size]`.
|
||||
|
||||
Returns:
|
||||
|
||||
Example:
|
||||
|
||||
```python
|
||||
>>> from PIL import Image
|
||||
>>> import requests
|
||||
>>> from transformers import AutoProcessor, PaliGemmaForConditionalGeneration
|
||||
|
||||
>>> model = PaliGemmaForConditionalGeneration.from_pretrained("google/PaliGemma-test-224px-hf")
|
||||
>>> processor = AutoProcessor.from_pretrained("google/PaliGemma-test-224px-hf")
|
||||
|
||||
>>> prompt = "answer en Where is the cow standing?"
|
||||
>>> url = "https://huggingface.co/gv-hf/PaliGemma-test-224px-hf/resolve/main/cow_beach_1.png"
|
||||
>>> image = Image.open(requests.get(url, stream=True).raw)
|
||||
|
||||
>>> inputs = processor(text=prompt, images=image, return_tensors="pt")
|
||||
|
||||
>>> # Generate
|
||||
>>> generate_ids = model.generate(**inputs, max_length=30)
|
||||
>>> processor.batch_decode(generate_ids, skip_special_tokens=True, clean_up_tokenization_spaces=False)[0]
|
||||
"answer en Where is the cow standing?\nbeach"
|
||||
```"""
|
||||
|
||||
if (input_ids is None) ^ (inputs_embeds is not None):
|
||||
raise ValueError(
|
||||
"You cannot specify both input_ids and inputs_embeds at the same time, and must specify either one"
|
||||
)
|
||||
|
||||
output_attentions = output_attentions if output_attentions is not None else self.config.output_attentions
|
||||
output_hidden_states = (
|
||||
output_hidden_states if output_hidden_states is not None else self.config.output_hidden_states
|
||||
)
|
||||
return_dict = return_dict if return_dict is not None else self.config.use_return_dict
|
||||
|
||||
# the attention mask is turned 4d after, we keep track of the original one
|
||||
input_attention_mask = attention_mask
|
||||
|
||||
if inputs_embeds is None:
|
||||
# 1. Extra the input embeddings
|
||||
inputs_embeds = self.get_input_embeddings()(input_ids)
|
||||
|
||||
# 2. Merge text and images
|
||||
if pixel_values is not None and input_ids.shape[1] != 1:
|
||||
image_outputs = self.vision_tower(pixel_values.to(inputs_embeds.dtype))
|
||||
selected_image_feature = image_outputs.last_hidden_state
|
||||
image_features = self.multi_modal_projector(selected_image_feature)
|
||||
|
||||
if cache_position is None:
|
||||
cache_position = torch.arange(inputs_embeds.shape[1], device=inputs_embeds.device)
|
||||
inputs_embeds, attention_mask, labels, position_ids = self._merge_input_ids_with_image_features(
|
||||
image_features, inputs_embeds, input_ids, attention_mask, labels, token_type_ids, cache_position
|
||||
)
|
||||
|
||||
else:
|
||||
# In case input_ids.shape[1] == 1 & pixel_values==None & past_key_values != None, we are in the case of
|
||||
# generation with cache
|
||||
if past_key_values is not None and pixel_values is not None and input_ids.shape[1] == 1:
|
||||
# Retrieve the first layer to inspect the logits and mask out the hidden states
|
||||
# that are set to 0
|
||||
# TODO @molbap this will only work for dynamic cache.
|
||||
first_layer_past_key_value = past_key_values[0][0][:, :, :, 0]
|
||||
|
||||
# Sum all dimensions of head_dim (-2) to avoid random errors such as: https://github.com/huggingface/transformers/pull/28032#issuecomment-1863691941
|
||||
batch_index, non_attended_tokens = torch.where(first_layer_past_key_value.float().sum(-2) == 0)
|
||||
|
||||
# Get the target length
|
||||
target_seqlen = cache_position[-1] + 1
|
||||
extended_attention_mask = torch.ones(
|
||||
(attention_mask.shape[0], target_seqlen - attention_mask.shape[1] + 1),
|
||||
dtype=attention_mask.dtype,
|
||||
device=attention_mask.device,
|
||||
)
|
||||
# Filter out only the tokens that can be un-attended, this can happen
|
||||
# if one uses PaliGemma+ Fused modules where the cache on the
|
||||
# first iteration is already big enough, or if one passes custom cache
|
||||
valid_indices = non_attended_tokens < extended_attention_mask.size(-1)
|
||||
new_batch_index = batch_index[valid_indices]
|
||||
new_non_attended_tokens = non_attended_tokens[valid_indices]
|
||||
|
||||
# Zero-out the places where we don't need to attend
|
||||
extended_attention_mask[new_batch_index, new_non_attended_tokens] = 0
|
||||
|
||||
attention_mask = torch.cat((attention_mask, extended_attention_mask), dim=1)
|
||||
position_ids = torch.sum(attention_mask, dim=1).unsqueeze(-1) - 1
|
||||
|
||||
attention_mask = attention_mask.to(inputs_embeds.dtype)
|
||||
outputs = self.language_model.model(
|
||||
attention_mask=attention_mask,
|
||||
position_ids=position_ids,
|
||||
past_key_values=past_key_values,
|
||||
inputs_embeds=inputs_embeds,
|
||||
use_cache=use_cache,
|
||||
output_attentions=output_attentions,
|
||||
output_hidden_states=output_hidden_states,
|
||||
return_dict=return_dict,
|
||||
cache_position=cache_position,
|
||||
)
|
||||
|
||||
hidden_states = outputs[0]
|
||||
|
||||
loss = None
|
||||
logits = None
|
||||
|
||||
if self.training and (labels is not None):
|
||||
shift_hidden_states = hidden_states[..., :-1, :]
|
||||
shift_labels = labels[..., 1:]
|
||||
|
||||
hidden_device = shift_hidden_states.device
|
||||
|
||||
if attention_mask is not None:
|
||||
# we use the input attention mask to shift the hidden_states and labels, because it is 2D.
|
||||
# we also crop attn mask in case it is longer, which happens in PrefixTuning with peft
|
||||
shift_attention_mask = attention_mask[:, -shift_hidden_states.shape[1] :].to(hidden_device)
|
||||
shift_hidden_states = shift_hidden_states[shift_attention_mask.to(hidden_device) != 0].contiguous()
|
||||
shift_labels = shift_labels[shift_attention_mask.to(shift_labels.device) != 0].contiguous()
|
||||
else:
|
||||
shift_hidden_states = shift_hidden_states.contiguous()
|
||||
shift_labels = shift_labels.contiguous()
|
||||
|
||||
# Flatten hidden state
|
||||
shift_hidden_states = shift_hidden_states.view(-1, self.config.text_config.hidden_size)
|
||||
shift_labels = shift_labels.view(-1).to(hidden_device)
|
||||
|
||||
lce = LigerFusedLinearCrossEntropyLoss()
|
||||
loss = lce(self.language_model.lm_head.weight, shift_hidden_states, shift_labels)
|
||||
|
||||
else:
|
||||
logits = self.language_model.lm_head(hidden_states)
|
||||
if labels is not None:
|
||||
shift_logits = logits[..., :-1, :]
|
||||
shift_labels = labels[..., 1:]
|
||||
if input_attention_mask is not None:
|
||||
# we use the input attention mask to shift the logits and labels, because it is 2D.
|
||||
shift_attention_mask = input_attention_mask[..., 1:]
|
||||
shift_logits = shift_logits[shift_attention_mask.to(logits.device) != 0].contiguous()
|
||||
shift_labels = shift_labels[shift_attention_mask.to(shift_labels.device) != 0].contiguous()
|
||||
else:
|
||||
shift_logits = shift_logits.contiguous()
|
||||
shift_labels = shift_labels.contiguous()
|
||||
# Flatten the tokens
|
||||
loss_fct = CrossEntropyLoss()
|
||||
|
||||
flat_logits = shift_logits.view(-1, self.config.vocab_size)
|
||||
flat_labels = shift_labels.view(-1).to(shift_logits.device)
|
||||
loss = loss_fct(flat_logits, flat_labels)
|
||||
if not return_dict:
|
||||
output = (logits,) + outputs[1:]
|
||||
return (loss,) + output if loss is not None else output
|
||||
|
||||
return PaliGemmaCausalLMOutputWithPast(
|
||||
loss=loss,
|
||||
logits=logits,
|
||||
past_key_values=outputs.past_key_values,
|
||||
hidden_states=outputs.hidden_states,
|
||||
attentions=outputs.attentions,
|
||||
)
|
||||
|
||||
|
||||
@deprecate_kwarg("num_logits_to_keep", version="4.50", new_name="logits_to_keep")
|
||||
def lce_forward(
|
||||
self,
|
||||
input_ids: torch.LongTensor = None,
|
||||
|
||||
@@ -7,7 +7,6 @@ import torch
|
||||
|
||||
from torch.nn import CrossEntropyLoss
|
||||
from transformers.modeling_outputs import CausalLMOutputWithPast
|
||||
from transformers.utils.deprecation import deprecate_kwarg
|
||||
|
||||
from liger_kernel.transformers.fused_linear_cross_entropy import LigerFusedLinearCrossEntropyLoss
|
||||
from liger_kernel.transformers.model.loss_utils import LigerForCausalLMLoss
|
||||
@@ -130,7 +129,6 @@ def lce_forward_deprecated(
|
||||
)
|
||||
|
||||
|
||||
@deprecate_kwarg("num_logits_to_keep", version="4.50", new_name="logits_to_keep")
|
||||
def lce_forward(
|
||||
self,
|
||||
input_ids: torch.LongTensor = None,
|
||||
|
||||
@@ -5,12 +5,30 @@ from typing import Union
|
||||
|
||||
import torch
|
||||
|
||||
from packaging import version
|
||||
from transformers import __version__ as transformers_version
|
||||
from transformers.utils import can_return_tuple
|
||||
|
||||
from liger_kernel.transformers.model.loss_utils import LigerForCausalLMLoss
|
||||
from liger_kernel.transformers.model.loss_utils import unpack_cross_entropy_result
|
||||
from liger_kernel.transformers.model.output_classes import LigerQwen2_5_VLCausalLMOutputWithPast
|
||||
|
||||
_TRANSFORMERS_V5_OR_LATER = version.parse(transformers_version) >= version.parse("5.0.0")
|
||||
|
||||
|
||||
def _get_hidden_size(config) -> int:
|
||||
"""Get hidden_size from Qwen2.5VLConfig in a version-aware manner."""
|
||||
if _TRANSFORMERS_V5_OR_LATER:
|
||||
return config.text_config.hidden_size
|
||||
return config.hidden_size
|
||||
|
||||
|
||||
def _get_vocab_size(config) -> int:
|
||||
"""Get vocab_size from Qwen2.5VLConfig in a version-aware manner."""
|
||||
if _TRANSFORMERS_V5_OR_LATER:
|
||||
return config.text_config.vocab_size
|
||||
return config.vocab_size
|
||||
|
||||
|
||||
@can_return_tuple
|
||||
def lce_forward(
|
||||
@@ -129,7 +147,7 @@ def lce_forward(
|
||||
lm_head_weight=self.lm_head.weight,
|
||||
labels=labels,
|
||||
shift_labels=shift_labels,
|
||||
hidden_size=self.config.hidden_size,
|
||||
hidden_size=_get_hidden_size(self.config),
|
||||
**kwargs,
|
||||
)
|
||||
loss, _, token_accuracy = unpack_cross_entropy_result(result)
|
||||
@@ -142,7 +160,7 @@ def lce_forward(
|
||||
logits=logits,
|
||||
labels=labels,
|
||||
shift_labels=shift_labels,
|
||||
vocab_size=self.config.vocab_size,
|
||||
vocab_size=_get_vocab_size(self.config),
|
||||
)
|
||||
|
||||
if not return_dict:
|
||||
|
||||
@@ -5,12 +5,30 @@ from typing import Union
|
||||
|
||||
import torch
|
||||
|
||||
from packaging import version
|
||||
from transformers import __version__ as transformers_version
|
||||
from transformers.utils import can_return_tuple
|
||||
|
||||
from liger_kernel.transformers.model.loss_utils import LigerForCausalLMLoss
|
||||
from liger_kernel.transformers.model.loss_utils import unpack_cross_entropy_result
|
||||
from liger_kernel.transformers.model.output_classes import LigerQwen2VLCausalLMOutputWithPast
|
||||
|
||||
_TRANSFORMERS_V5_OR_LATER = version.parse(transformers_version) >= version.parse("5.0.0")
|
||||
|
||||
|
||||
def _get_hidden_size(config) -> int:
|
||||
"""Get hidden_size from Qwen2VLConfig in a version-aware manner."""
|
||||
if _TRANSFORMERS_V5_OR_LATER:
|
||||
return config.text_config.hidden_size
|
||||
return config.hidden_size
|
||||
|
||||
|
||||
def _get_vocab_size(config) -> int:
|
||||
"""Get vocab_size from Qwen2VLConfig in a version-aware manner."""
|
||||
if _TRANSFORMERS_V5_OR_LATER:
|
||||
return config.text_config.vocab_size
|
||||
return config.vocab_size
|
||||
|
||||
|
||||
@can_return_tuple
|
||||
def lce_forward(
|
||||
@@ -125,7 +143,7 @@ def lce_forward(
|
||||
lm_head_weight=self.lm_head.weight,
|
||||
labels=labels,
|
||||
shift_labels=shift_labels,
|
||||
hidden_size=self.config.hidden_size,
|
||||
hidden_size=_get_hidden_size(self.config),
|
||||
**kwargs,
|
||||
)
|
||||
loss, _, token_accuracy = unpack_cross_entropy_result(result)
|
||||
@@ -138,7 +156,7 @@ def lce_forward(
|
||||
logits=logits,
|
||||
labels=labels,
|
||||
shift_labels=shift_labels,
|
||||
vocab_size=self.config.vocab_size,
|
||||
vocab_size=_get_vocab_size(self.config),
|
||||
)
|
||||
|
||||
if not return_dict:
|
||||
|
||||
@@ -7,7 +7,6 @@ from typing import Union
|
||||
import torch
|
||||
|
||||
from torch.distributed.fsdp import FullyShardedDataParallel
|
||||
from transformers.utils.deprecation import deprecate_kwarg
|
||||
|
||||
from liger_kernel.transformers.fsdp import _FSDPForwardRedirection
|
||||
from liger_kernel.transformers.model.loss_utils import LigerForCausalLMLoss
|
||||
@@ -22,7 +21,6 @@ if PEFT_AVAILABLE:
|
||||
from peft.utils.other import ModulesToSaveWrapper
|
||||
|
||||
|
||||
@deprecate_kwarg("num_logits_to_keep", version="4.50", new_name="logits_to_keep")
|
||||
def lce_forward(
|
||||
self,
|
||||
input_ids: torch.LongTensor = None,
|
||||
|
||||
@@ -17,26 +17,21 @@ from liger_kernel.transformers.geglu import LigerGEGLUMLP
|
||||
from liger_kernel.transformers.layer_norm import LigerLayerNorm
|
||||
from liger_kernel.transformers.model.falcon_h1 import lce_forward as falcon_h1_lce_forward
|
||||
from liger_kernel.transformers.model.gemma import lce_forward as gemma_lce_forward
|
||||
from liger_kernel.transformers.model.gemma import lce_forward_deprecated as gemma_lce_forward_deprecated
|
||||
from liger_kernel.transformers.model.gemma2 import lce_forward as gemma2_lce_forward
|
||||
from liger_kernel.transformers.model.gemma2 import lce_forward_deprecated as gemma2_lce_forward_deprected
|
||||
from liger_kernel.transformers.model.gpt_oss import lce_forward as gpt_oss_lce_forward
|
||||
from liger_kernel.transformers.model.llama import lce_forward as llama_lce_forward
|
||||
from liger_kernel.transformers.model.llama import lce_forward_deprecated as llama_lce_forward_deprecated
|
||||
from liger_kernel.transformers.model.llava import lce_forward as llava_lce_forward
|
||||
from liger_kernel.transformers.model.llava import lce_forward_deprecated as llava_lce_forward_deprecated
|
||||
from liger_kernel.transformers.model.mistral import lce_forward as mistral_lce_forward
|
||||
from liger_kernel.transformers.model.mixtral import lce_forward as mixtral_lce_forward
|
||||
from liger_kernel.transformers.model.mixtral import lce_forward_deprecated as mixtral_lce_forward_deprecated
|
||||
from liger_kernel.transformers.model.phi3 import lce_forward as phi3_lce_forward
|
||||
from liger_kernel.transformers.model.qwen2 import lce_forward as qwen2_lce_forward
|
||||
from liger_kernel.transformers.model.qwen2 import lce_forward_deprecated as qwen2_lce_forward_deprecated
|
||||
from liger_kernel.transformers.model.smollm3 import lce_forward as smollm3_lce_forward
|
||||
from liger_kernel.transformers.qwen2vl_mrope import liger_multimodal_rotary_pos_emb
|
||||
from liger_kernel.transformers.rms_norm import LigerRMSNorm
|
||||
from liger_kernel.transformers.rope import liger_rotary_pos_emb
|
||||
from liger_kernel.transformers.rope import liger_rotary_pos_emb_vision
|
||||
from liger_kernel.transformers.swiglu import LigerBlockSparseTop2MLP
|
||||
from liger_kernel.transformers.swiglu import LigerExperts
|
||||
from liger_kernel.transformers.swiglu import LigerPhi3SwiGLUMLP
|
||||
from liger_kernel.transformers.swiglu import LigerSwiGLUMLP
|
||||
|
||||
@@ -50,8 +45,15 @@ except ImportError:
|
||||
transformer_version = version.parse(transformers.__version__)
|
||||
|
||||
logger = logging.getLogger(__name__)
|
||||
SUPPORTED_TRANSFORMER_VERSION = "4.46.1"
|
||||
TRANSFORMER_DEPRECATION_WARNING = "Support for transformers versions < 4.46.1 will soon be discontinued due to issues with incorrect gradient accumulation. \n Please consider upgrading to avoid potential issues. See details: https://github.com/huggingface/transformers/pull/34191"
|
||||
|
||||
MIN_SUPPORTED_TRANSFORMERS_VERSION = version.parse("4.52.0")
|
||||
if transformer_version < MIN_SUPPORTED_TRANSFORMERS_VERSION:
|
||||
raise ImportError(
|
||||
f"liger-kernel requires transformers >= {MIN_SUPPORTED_TRANSFORMERS_VERSION}, got {transformers.__version__}. "
|
||||
"Please install an older version of liger-kernel that is compatible with your transformers version."
|
||||
)
|
||||
|
||||
IS_TRANSFORMERS_V5_OR_LATER = version.parse(transformers.__version__) >= version.parse("5.0.0")
|
||||
|
||||
|
||||
def _bind_method_to_module(module, method_name: str, new_method: Callable):
|
||||
@@ -183,13 +185,9 @@ def apply_liger_kernel_to_granite(
|
||||
modeling_granite.apply_rotary_pos_emb = liger_rotary_pos_emb
|
||||
|
||||
if cross_entropy:
|
||||
if transformer_version >= version.parse(SUPPORTED_TRANSFORMER_VERSION):
|
||||
from transformers.loss.loss_utils import nn
|
||||
from transformers.loss.loss_utils import nn
|
||||
|
||||
nn.functional.cross_entropy = liger_cross_entropy
|
||||
else:
|
||||
logger.warning(TRANSFORMER_DEPRECATION_WARNING)
|
||||
modeling_granite.CrossEntropyLoss = LigerCrossEntropyLoss
|
||||
nn.functional.cross_entropy = liger_cross_entropy
|
||||
|
||||
if fused_linear_cross_entropy:
|
||||
raise NotImplementedError("LigerFusedLinearCrossEntropy is not available for Granite models.")
|
||||
@@ -255,26 +253,15 @@ def apply_liger_kernel_to_llama(
|
||||
modeling_llama.LlamaMLP = LigerSwiGLUMLP
|
||||
|
||||
if cross_entropy:
|
||||
if transformer_version >= version.parse(SUPPORTED_TRANSFORMER_VERSION):
|
||||
from transformers.loss.loss_utils import nn
|
||||
from transformers.loss.loss_utils import nn
|
||||
|
||||
nn.functional.cross_entropy = liger_cross_entropy
|
||||
else:
|
||||
logger.warning(TRANSFORMER_DEPRECATION_WARNING)
|
||||
modeling_llama.CrossEntropyLoss = LigerCrossEntropyLoss
|
||||
nn.functional.cross_entropy = liger_cross_entropy
|
||||
|
||||
if fused_linear_cross_entropy:
|
||||
if transformer_version >= version.parse(SUPPORTED_TRANSFORMER_VERSION):
|
||||
if model is not None:
|
||||
model.forward = MethodType(llama_lce_forward, model)
|
||||
else:
|
||||
modeling_llama.LlamaForCausalLM.forward = llama_lce_forward
|
||||
else: # if version < 4.46.1
|
||||
logger.warning(TRANSFORMER_DEPRECATION_WARNING)
|
||||
if model is not None:
|
||||
model.forward = MethodType(llama_lce_forward_deprecated, model)
|
||||
else:
|
||||
modeling_llama.LlamaForCausalLM.forward = llama_lce_forward_deprecated
|
||||
if model is not None:
|
||||
model.forward = MethodType(llama_lce_forward, model)
|
||||
else:
|
||||
modeling_llama.LlamaForCausalLM.forward = llama_lce_forward
|
||||
|
||||
if model is not None:
|
||||
# The model instance already exists, so we need to additionally patch the
|
||||
@@ -333,13 +320,9 @@ def apply_liger_kernel_to_smollm3(
|
||||
modeling_smollm3.SmolLM3MLP = LigerSwiGLUMLP
|
||||
|
||||
if cross_entropy:
|
||||
if transformer_version >= version.parse(SUPPORTED_TRANSFORMER_VERSION):
|
||||
from transformers.loss.loss_utils import nn
|
||||
from transformers.loss.loss_utils import nn
|
||||
|
||||
nn.functional.cross_entropy = liger_cross_entropy
|
||||
else:
|
||||
logger.warning(TRANSFORMER_DEPRECATION_WARNING)
|
||||
modeling_smollm3.CrossEntropyLoss = LigerCrossEntropyLoss
|
||||
nn.functional.cross_entropy = liger_cross_entropy
|
||||
|
||||
if fused_linear_cross_entropy:
|
||||
if model is not None:
|
||||
@@ -396,23 +379,14 @@ def apply_liger_kernel_to_llava(
|
||||
from transformers.models.llava import modeling_llava
|
||||
|
||||
if cross_entropy:
|
||||
logger.warning(TRANSFORMER_DEPRECATION_WARNING)
|
||||
modeling_llava.nn.CrossEntropyLoss = LigerCrossEntropyLoss
|
||||
from transformers.loss.loss_utils import nn
|
||||
|
||||
nn.functional.cross_entropy = liger_cross_entropy
|
||||
if fused_linear_cross_entropy:
|
||||
if transformer_version >= version.parse("4.52.0"):
|
||||
if model is not None:
|
||||
model.forward = MethodType(llava_lce_forward, model)
|
||||
else:
|
||||
modeling_llava.LlavaForConditionalGeneration.forward = llava_lce_forward
|
||||
elif transformer_version >= version.parse("4.49.0") and transformer_version < version.parse("4.52.0"):
|
||||
if model is not None:
|
||||
model.forward = MethodType(llava_lce_forward_deprecated, model)
|
||||
else:
|
||||
modeling_llava.LlavaForConditionalGeneration.forward = llava_lce_forward_deprecated
|
||||
else: # if version < 4.49.0
|
||||
logger.warning(
|
||||
"The latest version of Liger does not support transformers < 4.49.0 for llava. Please downgrade your liger version or upgrade your transformer version."
|
||||
)
|
||||
if model is not None:
|
||||
model.forward = MethodType(llava_lce_forward, model)
|
||||
else:
|
||||
modeling_llava.LlavaForConditionalGeneration.forward = llava_lce_forward
|
||||
|
||||
if model is not None:
|
||||
text_model_name, vision_model_name = model.config.text_config.model_type, model.config.vision_config.model_type
|
||||
@@ -579,7 +553,6 @@ def apply_liger_kernel_to_mllama(
|
||||
from transformers.models.mllama.modeling_mllama import MllamaVisionModel
|
||||
|
||||
from liger_kernel.transformers.model.mllama import lce_forward as mllama_lce_forward
|
||||
from liger_kernel.transformers.model.mllama import lce_forward_deprecated as mllama_lce_forward_deprecated
|
||||
|
||||
if rope:
|
||||
modeling_mllama.apply_rotary_pos_emb = liger_rotary_pos_emb
|
||||
@@ -590,25 +563,14 @@ def apply_liger_kernel_to_mllama(
|
||||
if swiglu:
|
||||
modeling_mllama.MllamaTextMLP = LigerSwiGLUMLP
|
||||
if cross_entropy:
|
||||
if transformer_version >= version.parse(SUPPORTED_TRANSFORMER_VERSION):
|
||||
from transformers.loss.loss_utils import nn
|
||||
from transformers.loss.loss_utils import nn
|
||||
|
||||
nn.functional.cross_entropy = liger_cross_entropy
|
||||
else:
|
||||
logger.warning(TRANSFORMER_DEPRECATION_WARNING)
|
||||
modeling_mllama.CrossEntropyLoss = LigerCrossEntropyLoss
|
||||
nn.functional.cross_entropy = liger_cross_entropy
|
||||
if fused_linear_cross_entropy:
|
||||
if transformer_version >= version.parse(SUPPORTED_TRANSFORMER_VERSION):
|
||||
if model is not None:
|
||||
model.forward = MethodType(mllama_lce_forward, model)
|
||||
else:
|
||||
modeling_mllama.MllamaForCausalLM.forward = mllama_lce_forward
|
||||
else: # if version < 4.46.1
|
||||
logger.warning(TRANSFORMER_DEPRECATION_WARNING)
|
||||
if model is not None:
|
||||
model.forward = MethodType(mllama_lce_forward_deprecated, model)
|
||||
else:
|
||||
modeling_mllama.MllamaForCausalLM.forward = mllama_lce_forward_deprecated
|
||||
if model is not None:
|
||||
model.forward = MethodType(mllama_lce_forward, model)
|
||||
else:
|
||||
modeling_mllama.MllamaForCausalLM.forward = mllama_lce_forward
|
||||
|
||||
if model is not None:
|
||||
# The model instance already exists, so we need to additionally patch the
|
||||
@@ -694,16 +656,10 @@ def apply_liger_kernel_to_mistral(
|
||||
if cross_entropy:
|
||||
modeling_mistral.CrossEntropyLoss = LigerCrossEntropyLoss
|
||||
if fused_linear_cross_entropy:
|
||||
if transformer_version >= version.parse("4.49.0"):
|
||||
if model is not None:
|
||||
model.forward = MethodType(mistral_lce_forward, model)
|
||||
else:
|
||||
modeling_mistral.MistralForCausalLM.forward = mistral_lce_forward
|
||||
if model is not None:
|
||||
model.forward = MethodType(mistral_lce_forward, model)
|
||||
else:
|
||||
logger.warning(
|
||||
"The latest version of Liger does not support transformers < 4.49.0 for llava. Please downgrade your liger version or upgrade your transformer version."
|
||||
)
|
||||
logger.warning("LigerFusedLinearCrossEntropy patch is not applied.")
|
||||
modeling_mistral.MistralForCausalLM.forward = mistral_lce_forward
|
||||
|
||||
if swiglu:
|
||||
modeling_mistral.MistralMLP = LigerSwiGLUMLP
|
||||
@@ -762,28 +718,20 @@ def apply_liger_kernel_to_mixtral(
|
||||
if rms_norm:
|
||||
modeling_mixtral.MixtralRMSNorm = LigerRMSNorm
|
||||
if cross_entropy:
|
||||
if transformer_version >= version.parse(SUPPORTED_TRANSFORMER_VERSION):
|
||||
from transformers.loss.loss_utils import nn
|
||||
from transformers.loss.loss_utils import nn
|
||||
|
||||
nn.functional.cross_entropy = liger_cross_entropy
|
||||
else:
|
||||
logger.warning(TRANSFORMER_DEPRECATION_WARNING)
|
||||
modeling_mixtral.CrossEntropyLoss = LigerCrossEntropyLoss
|
||||
nn.functional.cross_entropy = liger_cross_entropy
|
||||
|
||||
if fused_linear_cross_entropy:
|
||||
if transformer_version >= version.parse(SUPPORTED_TRANSFORMER_VERSION):
|
||||
if model is not None:
|
||||
model.forward = MethodType(mixtral_lce_forward, model)
|
||||
else:
|
||||
modeling_mixtral.MixtralForCausalLM.forward = mixtral_lce_forward
|
||||
else: # if version < 4.46.1
|
||||
logger.warning(TRANSFORMER_DEPRECATION_WARNING)
|
||||
if model is not None:
|
||||
model.forward = MethodType(mixtral_lce_forward_deprecated, model)
|
||||
else:
|
||||
modeling_mixtral.MixtralForCausalLM.forward = mixtral_lce_forward_deprecated
|
||||
if model is not None:
|
||||
model.forward = MethodType(mixtral_lce_forward, model)
|
||||
else:
|
||||
modeling_mixtral.MixtralForCausalLM.forward = mixtral_lce_forward
|
||||
if swiglu:
|
||||
modeling_mixtral.MixtralBlockSparseTop2MLP = LigerBlockSparseTop2MLP
|
||||
if IS_TRANSFORMERS_V5_OR_LATER:
|
||||
modeling_mixtral.MixtralExperts = LigerExperts
|
||||
else:
|
||||
modeling_mixtral.MixtralBlockSparseTop2MLP = LigerBlockSparseTop2MLP
|
||||
|
||||
if model is not None:
|
||||
# The model instance already exists, so we need to additionally patch the
|
||||
@@ -797,8 +745,11 @@ def apply_liger_kernel_to_mixtral(
|
||||
|
||||
for decoder_layer in base_model.layers:
|
||||
if swiglu:
|
||||
for expert in decoder_layer.block_sparse_moe.experts:
|
||||
_patch_swiglu_module(expert, LigerBlockSparseTop2MLP)
|
||||
if IS_TRANSFORMERS_V5_OR_LATER:
|
||||
_patch_swiglu_module(decoder_layer.mlp.experts, LigerExperts)
|
||||
else:
|
||||
for expert in decoder_layer.block_sparse_moe.experts:
|
||||
_patch_swiglu_module(expert, LigerBlockSparseTop2MLP)
|
||||
if rms_norm:
|
||||
_patch_rms_norm_module(decoder_layer.input_layernorm)
|
||||
_patch_rms_norm_module(decoder_layer.post_attention_layernorm)
|
||||
@@ -844,27 +795,16 @@ def apply_liger_kernel_to_gemma(
|
||||
if rms_norm:
|
||||
modeling_gemma.GemmaRMSNorm = LigerRMSNormForGemma
|
||||
if cross_entropy:
|
||||
if transformer_version >= version.parse(SUPPORTED_TRANSFORMER_VERSION):
|
||||
from transformers.loss.loss_utils import nn
|
||||
from transformers.loss.loss_utils import nn
|
||||
|
||||
nn.functional.cross_entropy = liger_cross_entropy
|
||||
else:
|
||||
logger.warning(TRANSFORMER_DEPRECATION_WARNING)
|
||||
modeling_gemma.CrossEntropyLoss = LigerCrossEntropyLoss
|
||||
nn.functional.cross_entropy = liger_cross_entropy
|
||||
if geglu:
|
||||
modeling_gemma.GemmaMLP = LigerGEGLUMLP
|
||||
if fused_linear_cross_entropy:
|
||||
if transformer_version >= version.parse(SUPPORTED_TRANSFORMER_VERSION):
|
||||
if model is not None:
|
||||
model.forward = MethodType(gemma_lce_forward, model)
|
||||
else:
|
||||
modeling_gemma.GemmaForCausalLM.forward = gemma_lce_forward
|
||||
else: # if version < 4.46.1
|
||||
logger.warning(TRANSFORMER_DEPRECATION_WARNING)
|
||||
if model is not None:
|
||||
model.forward = MethodType(gemma_lce_forward_deprecated, model)
|
||||
else:
|
||||
modeling_gemma.GemmaForCausalLM.forward = gemma_lce_forward_deprecated
|
||||
if model is not None:
|
||||
model.forward = MethodType(gemma_lce_forward, model)
|
||||
else:
|
||||
modeling_gemma.GemmaForCausalLM.forward = gemma_lce_forward
|
||||
|
||||
if model is not None:
|
||||
# The model instance already exists, so we need to additionally patch the
|
||||
@@ -927,25 +867,14 @@ def apply_liger_kernel_to_gemma2(
|
||||
# https://github.com/huggingface/transformers/blob/v4.44.2/src/transformers/models/gemma/modeling_gemma.py#L109
|
||||
modeling_gemma2.Gemma2RMSNorm = LigerRMSNormForGemma2
|
||||
if cross_entropy:
|
||||
if transformer_version >= version.parse(SUPPORTED_TRANSFORMER_VERSION):
|
||||
from transformers.loss.loss_utils import nn
|
||||
from transformers.loss.loss_utils import nn
|
||||
|
||||
nn.functional.cross_entropy = liger_cross_entropy
|
||||
else:
|
||||
logger.warning(TRANSFORMER_DEPRECATION_WARNING)
|
||||
modeling_gemma2.CrossEntropyLoss = LigerCrossEntropyLoss
|
||||
nn.functional.cross_entropy = liger_cross_entropy
|
||||
if fused_linear_cross_entropy:
|
||||
if transformer_version >= version.parse(SUPPORTED_TRANSFORMER_VERSION):
|
||||
if model is not None:
|
||||
model.forward = MethodType(gemma2_lce_forward, model)
|
||||
else:
|
||||
modeling_gemma2.Gemma2ForCausalLM.forward = gemma2_lce_forward
|
||||
if model is not None:
|
||||
model.forward = MethodType(gemma2_lce_forward, model)
|
||||
else:
|
||||
logger.warning(TRANSFORMER_DEPRECATION_WARNING)
|
||||
if model is not None:
|
||||
model.forward = MethodType(gemma2_lce_forward_deprected, model)
|
||||
else:
|
||||
modeling_gemma2.Gemma2ForCausalLM.forward = gemma2_lce_forward_deprected
|
||||
modeling_gemma2.Gemma2ForCausalLM.forward = gemma2_lce_forward
|
||||
if geglu:
|
||||
modeling_gemma2.Gemma2MLP = LigerGEGLUMLP
|
||||
|
||||
@@ -1189,7 +1118,6 @@ def apply_liger_kernel_to_paligemma(
|
||||
from transformers.models.siglip.modeling_siglip import SiglipVisionModel
|
||||
|
||||
from liger_kernel.transformers.model.paligemma import lce_forward
|
||||
from liger_kernel.transformers.model.paligemma import lce_forward_deprecated
|
||||
|
||||
# The vision_tower is a SiglipVisionModel
|
||||
if layer_norm and model is None:
|
||||
@@ -1209,17 +1137,10 @@ def apply_liger_kernel_to_paligemma(
|
||||
if cross_entropy:
|
||||
modeling_paligemma.nn.CrossEntropyLoss = LigerCrossEntropyLoss
|
||||
if fused_linear_cross_entropy:
|
||||
if transformer_version >= version.parse(SUPPORTED_TRANSFORMER_VERSION):
|
||||
if model is not None:
|
||||
model.forward = MethodType(lce_forward, model)
|
||||
else:
|
||||
modeling_paligemma.PaliGemmaForConditionalGeneration.forward = lce_forward
|
||||
else: # if version < 4.46.1
|
||||
logger.warning(TRANSFORMER_DEPRECATION_WARNING)
|
||||
if model is not None:
|
||||
model.forward = MethodType(lce_forward_deprecated, model)
|
||||
else:
|
||||
modeling_paligemma.PaliGemmaForConditionalGeneration.forward = lce_forward_deprecated
|
||||
if model is not None:
|
||||
model.forward = MethodType(lce_forward, model)
|
||||
else:
|
||||
modeling_paligemma.PaliGemmaForConditionalGeneration.forward = lce_forward
|
||||
|
||||
if model is not None:
|
||||
# The model instance already exists, so we need to additionally patch the
|
||||
@@ -1301,26 +1222,15 @@ def apply_liger_kernel_to_qwen2(
|
||||
modeling_qwen2.Qwen2RMSNorm = LigerRMSNorm
|
||||
|
||||
if cross_entropy:
|
||||
if transformer_version >= version.parse(SUPPORTED_TRANSFORMER_VERSION):
|
||||
from transformers.loss.loss_utils import nn
|
||||
from transformers.loss.loss_utils import nn
|
||||
|
||||
nn.functional.cross_entropy = liger_cross_entropy
|
||||
else:
|
||||
logger.warning(TRANSFORMER_DEPRECATION_WARNING)
|
||||
modeling_qwen2.CrossEntropyLoss = LigerCrossEntropyLoss
|
||||
nn.functional.cross_entropy = liger_cross_entropy
|
||||
|
||||
if fused_linear_cross_entropy:
|
||||
if transformer_version >= version.parse(SUPPORTED_TRANSFORMER_VERSION):
|
||||
if model is not None:
|
||||
model.forward = MethodType(qwen2_lce_forward, model)
|
||||
else:
|
||||
modeling_qwen2.Qwen2ForCausalLM.forward = qwen2_lce_forward
|
||||
else: # if version < 4.46.1
|
||||
logger.warning(TRANSFORMER_DEPRECATION_WARNING)
|
||||
if model is not None:
|
||||
model.forward = MethodType(qwen2_lce_forward_deprecated, model)
|
||||
else:
|
||||
modeling_qwen2.Qwen2ForCausalLM.forward = qwen2_lce_forward_deprecated
|
||||
if model is not None:
|
||||
model.forward = MethodType(qwen2_lce_forward, model)
|
||||
else:
|
||||
modeling_qwen2.Qwen2ForCausalLM.forward = qwen2_lce_forward
|
||||
|
||||
if swiglu:
|
||||
modeling_qwen2.Qwen2MLP = LigerSwiGLUMLP
|
||||
@@ -1439,7 +1349,10 @@ def apply_liger_kernel_to_qwen3_moe(
|
||||
modeling_qwen3_moe.Qwen3MoeForCausalLM.forward = qwen3_lce_forward
|
||||
|
||||
if swiglu:
|
||||
modeling_qwen3_moe.Qwen3MoeMLP = LigerQwen3MoeSwiGLUMLP
|
||||
if IS_TRANSFORMERS_V5_OR_LATER:
|
||||
modeling_qwen3_moe.Qwen3MoeExperts = LigerExperts
|
||||
else:
|
||||
modeling_qwen3_moe.Qwen3MoeMLP = LigerQwen3MoeSwiGLUMLP
|
||||
|
||||
if model is not None:
|
||||
# The model instance already exists, so we need to additionally patch the
|
||||
@@ -1452,8 +1365,11 @@ def apply_liger_kernel_to_qwen3_moe(
|
||||
_patch_rms_norm_module(base_model.norm)
|
||||
for decoder_layer in base_model.layers:
|
||||
if swiglu:
|
||||
for mlp_expert in decoder_layer.mlp.experts:
|
||||
_patch_swiglu_module(mlp_expert, LigerQwen3MoeSwiGLUMLP)
|
||||
if IS_TRANSFORMERS_V5_OR_LATER:
|
||||
_patch_swiglu_module(decoder_layer.mlp.experts, LigerExperts)
|
||||
else:
|
||||
for mlp_expert in decoder_layer.mlp.experts:
|
||||
_patch_swiglu_module(mlp_expert, LigerQwen3MoeSwiGLUMLP)
|
||||
if rms_norm:
|
||||
_patch_rms_norm_module(decoder_layer.input_layernorm)
|
||||
_patch_rms_norm_module(decoder_layer.post_attention_layernorm)
|
||||
@@ -2671,8 +2587,11 @@ def apply_liger_kernel_to_qwen3_next(
|
||||
else:
|
||||
modeling_qwen3_next.Qwen3NextForCausalLM.forward = qwen3_next_lce_forward
|
||||
if swiglu:
|
||||
# Qwen3MoeMLP and Qwen3NextMLP are identical, hence we reuse LigerQwen3MoeSwiGLUMLP
|
||||
modeling_qwen3_next.Qwen3NextMLP = LigerQwen3MoeSwiGLUMLP
|
||||
if IS_TRANSFORMERS_V5_OR_LATER:
|
||||
modeling_qwen3_next.Qwen3NextExperts = LigerExperts
|
||||
else:
|
||||
# Qwen3MoeMLP and Qwen3NextMLP are identical, hence we reuse LigerQwen3MoeSwiGLUMLP
|
||||
modeling_qwen3_next.Qwen3NextMLP = LigerQwen3MoeSwiGLUMLP
|
||||
|
||||
if model is not None:
|
||||
# The model instance already exists, so we need to additionally patch the
|
||||
@@ -2700,8 +2619,11 @@ def apply_liger_kernel_to_qwen3_next(
|
||||
_patch_swiglu_module(decoder_layer.mlp.shared_expert, LigerQwen3MoeSwiGLUMLP)
|
||||
experts = getattr(decoder_layer.mlp, "experts", None)
|
||||
if experts is not None:
|
||||
for expert in experts:
|
||||
_patch_swiglu_module(expert, LigerQwen3MoeSwiGLUMLP)
|
||||
if IS_TRANSFORMERS_V5_OR_LATER:
|
||||
_patch_swiglu_module(experts, LigerExperts)
|
||||
else:
|
||||
for expert in experts:
|
||||
_patch_swiglu_module(expert, LigerQwen3MoeSwiGLUMLP)
|
||||
|
||||
|
||||
def apply_liger_kernel_to_hunyuan_v1_dense(
|
||||
@@ -2801,7 +2723,10 @@ def apply_liger_kernel_to_hunyuan_v1_moe(
|
||||
modeling_hunyuan_v1_moe.HunYuanMoEV1ForCausalLM.forward = hunyuan_v1_moe_lce_forward
|
||||
|
||||
if swiglu:
|
||||
modeling_hunyuan_v1_moe.HunYuanMoEV1MLP = LigerHunyuanV1SwiGLUMLP
|
||||
if IS_TRANSFORMERS_V5_OR_LATER:
|
||||
modeling_hunyuan_v1_moe.HunYuanMoEV1Experts = LigerExperts
|
||||
else:
|
||||
modeling_hunyuan_v1_moe.HunYuanMoEV1MLP = LigerHunyuanV1SwiGLUMLP
|
||||
|
||||
if model is not None:
|
||||
# The model instance already exists, so we need to additionally patch the
|
||||
@@ -2814,8 +2739,11 @@ def apply_liger_kernel_to_hunyuan_v1_moe(
|
||||
_patch_rms_norm_module(base_model.norm)
|
||||
for decoder_layer in base_model.layers:
|
||||
if swiglu:
|
||||
for mlp_expert in decoder_layer.mlp.experts:
|
||||
_patch_swiglu_module(mlp_expert, LigerHunyuanV1SwiGLUMLP)
|
||||
if IS_TRANSFORMERS_V5_OR_LATER:
|
||||
_patch_swiglu_module(decoder_layer.mlp.experts, LigerExperts)
|
||||
else:
|
||||
for mlp_expert in decoder_layer.mlp.experts:
|
||||
_patch_swiglu_module(mlp_expert, LigerHunyuanV1SwiGLUMLP)
|
||||
if rms_norm:
|
||||
_patch_rms_norm_module(decoder_layer.input_layernorm)
|
||||
_patch_rms_norm_module(decoder_layer.post_attention_layernorm)
|
||||
|
||||
@@ -1,3 +1,4 @@
|
||||
import torch
|
||||
import torch.nn as nn
|
||||
|
||||
from liger_kernel.ops import LigerSiLUMulFunction
|
||||
@@ -36,6 +37,54 @@ class LigerBlockSparseTop2MLP(nn.Module):
|
||||
return self.w2(LigerSiLUMulFunction.apply(self.w1(x), self.w3(x)))
|
||||
|
||||
|
||||
class LigerExperts(nn.Module):
|
||||
"""
|
||||
Patch MixtralExperts for transformers v5 or later to use LigerSiLUMulFunction
|
||||
https://github.com/huggingface/transformers/blob/393b4b3d28e29b4b05b19b4b7f3242a7fc893637/src/transformers/models/mixtral/modeling_mixtral.py#L63
|
||||
"""
|
||||
|
||||
def __init__(self, config):
|
||||
super().__init__()
|
||||
if "num_experts" in config:
|
||||
# qwen3_moe, qwen3_next uses num_experts
|
||||
self.num_experts = config.num_experts
|
||||
else:
|
||||
self.num_experts = config.num_local_experts
|
||||
if "moe_intermediate_size" in config:
|
||||
# qwen3_moe, qwen3_next uses moe_intermediate_size
|
||||
self.intermediate_dim = config.moe_intermediate_size
|
||||
else:
|
||||
self.intermediate_dim = config.intermediate_size
|
||||
|
||||
self.hidden_dim = config.hidden_size
|
||||
self.gate_up_proj = nn.Parameter(torch.empty(self.num_experts, 2 * self.intermediate_dim, self.hidden_dim))
|
||||
self.down_proj = nn.Parameter(torch.empty(self.num_experts, self.hidden_dim, self.intermediate_dim))
|
||||
|
||||
if config.hidden_act not in ["silu", "swish"]:
|
||||
raise ValueError(f"Activation function {config.hidden_act} not supported.")
|
||||
|
||||
def forward(self, hidden_states, top_k_index, top_k_weights):
|
||||
final_hidden_states = torch.zeros_like(hidden_states)
|
||||
with torch.no_grad():
|
||||
expert_mask = torch.nn.functional.one_hot(top_k_index, num_classes=self.num_experts)
|
||||
expert_mask = expert_mask.permute(2, 1, 0)
|
||||
expert_hit = torch.greater(expert_mask.sum(dim=(-1, -2)), 0).nonzero()
|
||||
|
||||
for expert_idx in expert_hit:
|
||||
expert_idx = expert_idx[0]
|
||||
if expert_idx == self.num_experts:
|
||||
continue
|
||||
top_k_pos, token_idx = torch.where(expert_mask[expert_idx])
|
||||
current_state = hidden_states[token_idx]
|
||||
gate, up = nn.functional.linear(current_state, self.gate_up_proj[expert_idx]).chunk(2, dim=-1)
|
||||
current_hidden_states = LigerSiLUMulFunction.apply(gate, up)
|
||||
current_hidden_states = nn.functional.linear(current_hidden_states, self.down_proj[expert_idx])
|
||||
current_hidden_states = current_hidden_states * top_k_weights[token_idx, top_k_pos, None]
|
||||
final_hidden_states.index_add_(0, token_idx, current_hidden_states.to(final_hidden_states.dtype))
|
||||
|
||||
return final_hidden_states
|
||||
|
||||
|
||||
class LigerPhi3SwiGLUMLP(nn.Module):
|
||||
"""
|
||||
Patch Phi3MLP to use LigerSiLUMulFunction
|
||||
|
||||
@@ -4,8 +4,10 @@ os.environ["CUBLAS_WORKSPACE_CONFIG"] = ":4096:8" # Ensure deterministic behavi
|
||||
|
||||
import pytest
|
||||
import torch
|
||||
import transformers
|
||||
|
||||
from datasets import load_from_disk
|
||||
from packaging import version
|
||||
from torch.utils.data import DataLoader
|
||||
from transformers.models.gemma import GemmaConfig
|
||||
from transformers.models.gemma import GemmaForCausalLM
|
||||
@@ -53,6 +55,7 @@ from liger_kernel.transformers import apply_liger_kernel_to_qwen3_next
|
||||
from liger_kernel.transformers import apply_liger_kernel_to_qwen3_vl
|
||||
from liger_kernel.transformers import apply_liger_kernel_to_qwen3_vl_moe
|
||||
from liger_kernel.transformers import apply_liger_kernel_to_smollm3
|
||||
from liger_kernel.utils import infer_device
|
||||
from test.utils import DEFAULT_DATASET_PATH
|
||||
from test.utils import MiniModelConfig
|
||||
from test.utils import assert_verbose_allclose
|
||||
@@ -94,6 +97,8 @@ from test.utils import set_seed
|
||||
from test.utils import simple_collate_fn
|
||||
from test.utils import supports_bfloat16
|
||||
|
||||
IS_TRANSFORMERS_V5_OR_LATER = version.parse(transformers.__version__) >= version.parse("5.0.0")
|
||||
|
||||
try:
|
||||
from transformers.models.llama4.configuration_llama4 import Llama4TextConfig
|
||||
from transformers.models.llama4.modeling_llama4 import Llama4ForCausalLM
|
||||
@@ -307,7 +312,6 @@ try:
|
||||
except ImportError:
|
||||
EXAONE4_AVAILABLE = False
|
||||
|
||||
from liger_kernel.utils import infer_device
|
||||
|
||||
device = infer_device()
|
||||
|
||||
@@ -333,8 +337,6 @@ MINI_MODEL_SETUPS = {
|
||||
num_key_value_heads=2, # 8
|
||||
pretraining_tp=1,
|
||||
rms_norm_eps=1e-5,
|
||||
rope_scaling=None,
|
||||
rope_theta=500000.0,
|
||||
tie_word_embeddings=False,
|
||||
use_cache=True,
|
||||
vocab_size=32000, # 128256,
|
||||
@@ -362,7 +364,6 @@ MINI_MODEL_SETUPS = {
|
||||
num_hidden_layers=4,
|
||||
num_key_value_heads=2,
|
||||
rms_norm_eps=1e-6,
|
||||
rope_theta=1000000.0,
|
||||
sliding_window=131072,
|
||||
tie_word_embeddings=True,
|
||||
use_cache=True,
|
||||
@@ -391,7 +392,6 @@ MINI_MODEL_SETUPS = {
|
||||
num_hidden_layers=4, # 32
|
||||
num_key_value_heads=None, # defaults to num_attention_heads
|
||||
rms_norm_eps=1e-5,
|
||||
rope_theta=10000.0,
|
||||
sliding_window=None,
|
||||
tie_word_embeddings=False,
|
||||
use_cache=True,
|
||||
@@ -416,7 +416,6 @@ MINI_MODEL_SETUPS = {
|
||||
num_hidden_layers=4,
|
||||
num_key_value_heads=2,
|
||||
rms_norm_eps=1e-5,
|
||||
rope_theta=10000.0,
|
||||
sliding_window=4096,
|
||||
tie_word_embeddings=False,
|
||||
use_cache=True,
|
||||
@@ -441,7 +440,6 @@ MINI_MODEL_SETUPS = {
|
||||
num_hidden_layers=4, # 32
|
||||
num_key_value_heads=2, # 8
|
||||
rms_norm_eps=1e-5,
|
||||
rope_theta=10000.0,
|
||||
sliding_window=4096,
|
||||
tie_word_embeddings=False,
|
||||
use_cache=True,
|
||||
@@ -476,7 +474,6 @@ MINI_MODEL_SETUPS = {
|
||||
bos_token_id=1, # 128000
|
||||
eos_token_id=2, # 128001
|
||||
tie_word_embeddings=True,
|
||||
rope_theta=10000.0,
|
||||
attention_bias=False,
|
||||
attention_dropout=0.0,
|
||||
),
|
||||
@@ -504,7 +501,6 @@ MINI_MODEL_SETUPS = {
|
||||
bos_token_id=1, # 128000
|
||||
eos_token_id=2, # 128001
|
||||
tie_word_embeddings=True,
|
||||
rope_theta=10000.0,
|
||||
attention_bias=False,
|
||||
attention_dropout=0.0,
|
||||
),
|
||||
@@ -532,7 +528,6 @@ MINI_MODEL_SETUPS = {
|
||||
bos_token_id=1, # 128000
|
||||
eos_token_id=2, # 128001
|
||||
tie_word_embeddings=True,
|
||||
rope_theta=10000.0,
|
||||
attention_bias=False,
|
||||
attention_dropout=0.0,
|
||||
attn_implementation="eager",
|
||||
@@ -561,8 +556,6 @@ if LLAMA4_AVAILABLE:
|
||||
num_hidden_layers=4, # 61
|
||||
num_key_value_heads=2,
|
||||
rms_norm_eps=1e-5,
|
||||
rope_scaling=None,
|
||||
rope_theta=10000.0,
|
||||
tie_word_embeddings=False,
|
||||
use_cache=True,
|
||||
vocab_size=32000, # 151552
|
||||
@@ -590,7 +583,6 @@ if QWEN3_AVAILABLE:
|
||||
num_hidden_layers=4,
|
||||
num_key_value_heads=2,
|
||||
rms_norm_eps=1e-6,
|
||||
rope_theta=1000000.0,
|
||||
sliding_window=131072,
|
||||
tie_word_embeddings=True,
|
||||
use_cache=True,
|
||||
@@ -616,8 +608,6 @@ if QWEN3_AVAILABLE:
|
||||
rms_norm_eps=1e-6,
|
||||
use_cache=True,
|
||||
tie_word_embeddings=False,
|
||||
rope_theta=10000.0,
|
||||
rope_scaling=None,
|
||||
attention_bias=False,
|
||||
use_sliding_window=False,
|
||||
sliding_window=4096,
|
||||
@@ -653,14 +643,6 @@ if GPT_OSS_AVAILABLE:
|
||||
rms_norm_eps=1e-5,
|
||||
use_cache=True,
|
||||
tie_word_embeddings=False,
|
||||
rope_parameters={
|
||||
"rope_type": "yarn",
|
||||
"factor": 8.0,
|
||||
"beta_fast": 32.0,
|
||||
"beta_slow": 1.0,
|
||||
"truncate": False,
|
||||
"original_max_position_embeddings": 4096,
|
||||
},
|
||||
attention_dropout=0.0,
|
||||
num_local_experts=8, # Reduced from 32 for mini model
|
||||
num_experts_per_tok=2, # Reduced from 4 for mini model
|
||||
@@ -693,7 +675,6 @@ if GEMMA3_AVAILABLE:
|
||||
bos_token_id=2,
|
||||
eos_token_id=1,
|
||||
tie_word_embeddings=True,
|
||||
rope_theta=10000.0, # 1000000
|
||||
attention_bias=False,
|
||||
attention_dropout=0.0,
|
||||
attn_implementation="eager",
|
||||
@@ -721,18 +702,20 @@ if MLLAMA_AVAILABLE:
|
||||
num_hidden_layers=4, # 40
|
||||
num_key_value_heads=2, # 8
|
||||
rms_norm_eps=1e-5,
|
||||
tie_word_embeddings=False,
|
||||
use_cache=True,
|
||||
vocab_size=32000, # 128256,
|
||||
attn_implementation="sdpa", # default value, pytorch native attention
|
||||
rope_scaling=dict(
|
||||
factor=8.0,
|
||||
high_freq_factor=4.0,
|
||||
low_freq_factor=1.0,
|
||||
original_max_position_embeddings=8192,
|
||||
rope_type="llama3",
|
||||
),
|
||||
rope_theta=500_000,
|
||||
tie_word_embeddings=False,
|
||||
use_cache=True,
|
||||
vocab_size=32000, # 128256,
|
||||
attn_implementation="sdpa", # default value, pytorch native attention
|
||||
rope_theta=500_000,
|
||||
)
|
||||
if not IS_TRANSFORMERS_V5_OR_LATER
|
||||
else None,
|
||||
),
|
||||
)
|
||||
|
||||
@@ -742,36 +725,38 @@ if QWEN2_VL_AVAILABLE:
|
||||
liger_kernel_patch_revert_func=revert_liger_kernel_to_qwen2_vl,
|
||||
model_class=Qwen2VLForConditionalGeneration,
|
||||
mini_model_config=Qwen2VLConfig(
|
||||
attention_dropout=0.0,
|
||||
# bos and eos set to match the Mistral-7B tokenizer used to create the test dataset
|
||||
# https://huggingface.co/mistralai/Mistral-7B-v0.1/blob/main/config.json
|
||||
bos_token_id=1, # 151643
|
||||
eos_token_id=2, # 151645
|
||||
# In transformers v5, text-related parameters must be in text_config
|
||||
text_config={
|
||||
"attention_dropout": 0.0,
|
||||
# bos and eos set to match the Mistral-7B tokenizer used to create the test dataset
|
||||
# https://huggingface.co/mistralai/Mistral-7B-v0.1/blob/main/config.json
|
||||
"bos_token_id": 1, # 151643
|
||||
"eos_token_id": 2, # 151645
|
||||
"hidden_act": "silu",
|
||||
"hidden_size": 1536, # 8192
|
||||
"initializer_range": 0.02,
|
||||
"intermediate_size": 4864, # 29568
|
||||
"max_position_embeddings": 32768,
|
||||
"max_window_layers": 4, # 80
|
||||
"num_attention_heads": 12, # 64
|
||||
"num_hidden_layers": 4, # 80
|
||||
"num_key_value_heads": 2, # 8
|
||||
"rms_norm_eps": 1e-6, # 1e-5
|
||||
**(
|
||||
{"rope_parameters": {"mrope_section": [16, 24, 24]}} # (temporal, height, width)
|
||||
if IS_TRANSFORMERS_V5_OR_LATER
|
||||
else {"rope_scaling": {"type": "mrope", "mrope_section": [16, 24, 24]}}
|
||||
),
|
||||
"sliding_window": 4096,
|
||||
"tie_word_embeddings": False,
|
||||
"use_cache": True,
|
||||
"vocab_size": 32768, # 152064 # >32k, Mistral-7B tokenizer vocab size
|
||||
"use_sliding_window": False,
|
||||
},
|
||||
vision_start_token_id=32765, # vocab_size - 5
|
||||
vision_end_token_id=32766, # vocab_size - 4
|
||||
vision_token_id=32767, # vocab_size - 3
|
||||
image_token_id=32768, # vocab_size - 2
|
||||
video_token_id=32769, # vocab_size - 1
|
||||
hidden_act="silu",
|
||||
hidden_size=1536, # 8192
|
||||
initializer_range=0.02,
|
||||
intermediate_size=4864, # 29568
|
||||
max_position_embeddings=32768,
|
||||
max_window_layers=4, # 80
|
||||
num_attention_heads=12, # 64
|
||||
num_hidden_layers=4, # 80
|
||||
num_key_value_heads=2, # 8
|
||||
rms_norm_eps=1e-6, # 1e-5
|
||||
rope_theta=1000000.0,
|
||||
rope_scaling=dict(
|
||||
type="mrope",
|
||||
mrope_section=[16, 24, 24], # (temporal, height, width)
|
||||
),
|
||||
sliding_window=4096,
|
||||
tie_word_embeddings=False,
|
||||
use_cache=True,
|
||||
vocab_size=32768, # 152064 # >32k, Mistral-7B tokenizer vocab size
|
||||
use_sliding_window=False,
|
||||
vision_config={
|
||||
"depth": 4, # 32
|
||||
"embed_dim": 1280,
|
||||
@@ -784,7 +769,6 @@ if QWEN2_VL_AVAILABLE:
|
||||
"spatial_patch_size": 14,
|
||||
"temporal_patch_size": 2,
|
||||
},
|
||||
attn_implementation="sdpa",
|
||||
),
|
||||
)
|
||||
|
||||
@@ -794,36 +778,38 @@ if QWEN2_5_VL_AVAILABLE:
|
||||
liger_kernel_patch_revert_func=revert_liger_kernel_to_qwen2_5_vl,
|
||||
model_class=Qwen2_5_VLForConditionalGeneration,
|
||||
mini_model_config=Qwen2_5_VLConfig(
|
||||
attention_dropout=0.0,
|
||||
# bos and eos set to match the Mistral-7B tokenizer used to create the test dataset
|
||||
# https://huggingface.co/mistralai/Mistral-7B-v0.1/blob/main/config.json
|
||||
bos_token_id=1, # 151643
|
||||
eos_token_id=2, # 151645
|
||||
# In transformers v5, text-related parameters must be in text_config
|
||||
text_config={
|
||||
"attention_dropout": 0.0,
|
||||
# bos and eos set to match the Mistral-7B tokenizer used to create the test dataset
|
||||
# https://huggingface.co/mistralai/Mistral-7B-v0.1/blob/main/config.json
|
||||
"bos_token_id": 1, # 151643
|
||||
"eos_token_id": 2, # 151645
|
||||
"hidden_act": "silu",
|
||||
"hidden_size": 1536, # 8192
|
||||
"initializer_range": 0.02,
|
||||
"intermediate_size": 4864, # 29568
|
||||
"max_position_embeddings": 32768,
|
||||
"max_window_layers": 4, # 80
|
||||
"num_attention_heads": 12, # 64
|
||||
"num_hidden_layers": 4, # 80
|
||||
"num_key_value_heads": 2, # 8
|
||||
"rms_norm_eps": 1e-6, # 1e-5
|
||||
**(
|
||||
{"rope_parameters": {"mrope_section": [16, 24, 24]}} # (temporal, height, width)
|
||||
if IS_TRANSFORMERS_V5_OR_LATER
|
||||
else {"rope_scaling": {"type": "mrope", "mrope_section": [16, 24, 24]}}
|
||||
),
|
||||
"sliding_window": 4096,
|
||||
"tie_word_embeddings": False,
|
||||
"use_cache": True,
|
||||
"vocab_size": 32768, # 152064 # >32k, Mistral-7B tokenizer vocab size
|
||||
"use_sliding_window": False,
|
||||
},
|
||||
vision_start_token_id=32765, # vocab_size - 5
|
||||
vision_end_token_id=32766, # vocab_size - 4
|
||||
vision_token_id=32767, # vocab_size - 3
|
||||
image_token_id=32768, # vocab_size - 2
|
||||
video_token_id=32769, # vocab_size - 1
|
||||
hidden_act="silu",
|
||||
hidden_size=1536, # 8192
|
||||
initializer_range=0.02,
|
||||
intermediate_size=4864, # 29568
|
||||
max_position_embeddings=32768,
|
||||
max_window_layers=4, # 80
|
||||
num_attention_heads=12, # 64
|
||||
num_hidden_layers=4, # 80
|
||||
num_key_value_heads=2, # 8
|
||||
rms_norm_eps=1e-6, # 1e-5
|
||||
rope_theta=1000000.0,
|
||||
rope_scaling=dict(
|
||||
type="mrope",
|
||||
mrope_section=[16, 24, 24], # (temporal, height, width)
|
||||
),
|
||||
sliding_window=4096,
|
||||
tie_word_embeddings=False,
|
||||
use_cache=True,
|
||||
vocab_size=32768, # 152064 # >32k, Mistral-7B tokenizer vocab size
|
||||
use_sliding_window=False,
|
||||
vision_config={
|
||||
"depth": 4, # 32
|
||||
"hidden_act": "silu",
|
||||
@@ -840,7 +826,6 @@ if QWEN2_5_VL_AVAILABLE:
|
||||
"tokens_per_second": 2,
|
||||
"temporal_patch_size": 2,
|
||||
},
|
||||
attn_implementation="sdpa",
|
||||
),
|
||||
)
|
||||
|
||||
@@ -870,13 +855,15 @@ if QWEN3_VL_AVAILABLE:
|
||||
num_hidden_layers=4,
|
||||
num_key_value_heads=2,
|
||||
rms_norm_eps=1e-6,
|
||||
rope_theta=1000000.0,
|
||||
rope_scaling=dict(
|
||||
type="mrope",
|
||||
mrope_section=[16, 24, 24],
|
||||
),
|
||||
use_cache=True,
|
||||
vocab_size=32768,
|
||||
pad_token_id=None,
|
||||
rope_scaling=dict(
|
||||
type="mrope",
|
||||
mrope_section=[16, 24, 24], # (temporal, height, width)
|
||||
)
|
||||
if not IS_TRANSFORMERS_V5_OR_LATER
|
||||
else None,
|
||||
),
|
||||
vision_config=dict(
|
||||
depth=4,
|
||||
@@ -923,11 +910,6 @@ if QWEN3_VL_MOE_AVAILABLE:
|
||||
num_key_value_heads=2,
|
||||
head_dim=128,
|
||||
rms_norm_eps=1e-6,
|
||||
rope_theta=1000000.0,
|
||||
rope_scaling=dict(
|
||||
type="mrope",
|
||||
mrope_section=[16, 24, 24],
|
||||
),
|
||||
use_cache=True,
|
||||
vocab_size=32768,
|
||||
decoder_sparse_step=1,
|
||||
@@ -936,6 +918,13 @@ if QWEN3_VL_MOE_AVAILABLE:
|
||||
num_experts=4,
|
||||
tie_word_embeddings=False,
|
||||
mlp_only_layers=[],
|
||||
pad_token_id=None,
|
||||
rope_scaling=dict(
|
||||
type="mrope",
|
||||
mrope_section=[16, 24, 24], # (temporal, height, width)
|
||||
)
|
||||
if not IS_TRANSFORMERS_V5_OR_LATER
|
||||
else None,
|
||||
).to_dict(),
|
||||
vision_config=Qwen3VLMoeVisionConfig(
|
||||
depth=4,
|
||||
@@ -977,8 +966,6 @@ if GRANITE_AVAILABLE:
|
||||
num_key_value_heads=2, # 8
|
||||
pretraining_tp=1,
|
||||
rms_norm_eps=1e-5,
|
||||
rope_scaling=None,
|
||||
rope_theta=500000.0,
|
||||
tie_word_embeddings=False,
|
||||
use_cache=True,
|
||||
vocab_size=32000, # 128256,
|
||||
@@ -1010,8 +997,6 @@ if LLAVA_AVAILABLE:
|
||||
num_hidden_layers=4,
|
||||
num_key_value_heads=2,
|
||||
pretraining_tp=1,
|
||||
rope_scaling=None,
|
||||
rope_theta=500000.0,
|
||||
tie_word_embeddings=False,
|
||||
use_cache=True,
|
||||
max_position_embeddings=4096, # llava-1.5-7b-hf
|
||||
@@ -1069,8 +1054,6 @@ if OLMO2_AVAILABLE:
|
||||
num_hidden_layers=4, # 40
|
||||
num_key_value_heads=2, # 8
|
||||
rms_norm_eps=1e-5,
|
||||
rope_scaling=None,
|
||||
rope_theta=500_000,
|
||||
tie_word_embeddings=False,
|
||||
use_cache=True,
|
||||
vocab_size=32000, # 128256,
|
||||
@@ -1098,8 +1081,6 @@ if OLMO3_AVAILABLE:
|
||||
num_hidden_layers=4, # 40
|
||||
num_key_value_heads=2, # 8
|
||||
rms_norm_eps=1e-5,
|
||||
rope_scaling=None,
|
||||
rope_theta=500_000,
|
||||
tie_word_embeddings=False,
|
||||
use_cache=True,
|
||||
vocab_size=32000, # 128256,
|
||||
@@ -1128,8 +1109,6 @@ if GLM4_AVAILABLE:
|
||||
num_hidden_layers=4, # 61
|
||||
num_key_value_heads=2,
|
||||
rms_norm_eps=1e-5,
|
||||
rope_scaling=None,
|
||||
rope_theta=500_000,
|
||||
tie_word_embeddings=False,
|
||||
use_cache=True,
|
||||
vocab_size=32000, # 151552
|
||||
@@ -1165,8 +1144,6 @@ if GLM4V_AVAILABLE:
|
||||
num_hidden_layers=4, # 61
|
||||
num_key_value_heads=2,
|
||||
rms_norm_eps=1e-5,
|
||||
rope_scaling=None,
|
||||
rope_theta=500_000,
|
||||
tie_word_embeddings=False,
|
||||
use_cache=True,
|
||||
vocab_size=32000, # 151552
|
||||
@@ -1182,13 +1159,14 @@ if GLM4V_AVAILABLE:
|
||||
"num_hidden_layers": 4,
|
||||
"num_key_value_heads": 2,
|
||||
"rms_norm_eps": 1e-5,
|
||||
"rope_scaling": {
|
||||
"type": "default",
|
||||
"mrope_section": [8, 12, 12], # (temporal, height, width)
|
||||
},
|
||||
"rope_theta": 500_000,
|
||||
"vocab_size": 32000,
|
||||
"attention_bias": True,
|
||||
**(
|
||||
{"rope_scaling": {"type": "default", "mrope_section": [8, 12, 12]}}
|
||||
if not IS_TRANSFORMERS_V5_OR_LATER
|
||||
else {}
|
||||
),
|
||||
"pad_token_id": None,
|
||||
},
|
||||
vision_config={
|
||||
"depth": 4, # 32
|
||||
@@ -1232,8 +1210,6 @@ if GLM4V_MOE_AVAILABLE:
|
||||
num_hidden_layers=4, # 61
|
||||
num_key_value_heads=2,
|
||||
rms_norm_eps=1e-5,
|
||||
rope_scaling=None,
|
||||
rope_theta=500_000,
|
||||
tie_word_embeddings=False,
|
||||
use_cache=True,
|
||||
vocab_size=32000, # 151552
|
||||
@@ -1249,11 +1225,6 @@ if GLM4V_MOE_AVAILABLE:
|
||||
"num_hidden_layers": 4,
|
||||
"num_key_value_heads": 2,
|
||||
"rms_norm_eps": 1e-5,
|
||||
"rope_scaling": {
|
||||
"type": "default",
|
||||
"mrope_section": [8, 12, 12], # (temporal, height, width)
|
||||
},
|
||||
"rope_theta": 500_000,
|
||||
"vocab_size": 32000,
|
||||
"attention_bias": True,
|
||||
"attention_dropout": 0.0,
|
||||
@@ -1266,6 +1237,11 @@ if GLM4V_MOE_AVAILABLE:
|
||||
"topk_group": 1,
|
||||
"first_k_dense_replace": 1,
|
||||
"norm_topk_prob": True,
|
||||
**(
|
||||
{"rope_scaling": {"type": "default", "mrope_section": [8, 12, 12]}}
|
||||
if not IS_TRANSFORMERS_V5_OR_LATER
|
||||
else {}
|
||||
),
|
||||
},
|
||||
vision_config={
|
||||
"depth": 4, # 32
|
||||
@@ -1303,8 +1279,6 @@ if SMOLLM3_AVAILABLE:
|
||||
num_key_value_heads=2, # 8
|
||||
pretraining_tp=1,
|
||||
rms_norm_eps=1e-5,
|
||||
rope_scaling=None,
|
||||
rope_theta=500000.0,
|
||||
tie_word_embeddings=False,
|
||||
use_cache=True,
|
||||
vocab_size=32000, # 128256,
|
||||
@@ -1396,8 +1370,6 @@ if QWEN3NEXT_AVAILABLE:
|
||||
rms_norm_eps=1e-6,
|
||||
use_cache=True,
|
||||
tie_word_embeddings=False,
|
||||
rope_theta=10000.0,
|
||||
rope_scaling=None,
|
||||
attention_bias=False,
|
||||
use_sliding_window=False,
|
||||
sliding_window=4096,
|
||||
@@ -1437,7 +1409,6 @@ if HUNYUAN_V1_AVAILABLE:
|
||||
initializer_range=0.02,
|
||||
norm_eps=1e-6,
|
||||
num_key_value_heads=2,
|
||||
rope_theta=10000.0,
|
||||
partial_rotary_factor=1.0,
|
||||
vocab_size=32000,
|
||||
use_cache=True,
|
||||
@@ -1468,8 +1439,6 @@ if HUNYUAN_V1_AVAILABLE:
|
||||
eod_token_id=3,
|
||||
sep_token_id=4,
|
||||
tie_word_embeddings=False,
|
||||
rope_theta=10000.0,
|
||||
rope_scaling=None,
|
||||
attention_bias=False,
|
||||
attention_dropout=0.0,
|
||||
num_experts=2,
|
||||
@@ -1496,11 +1465,11 @@ if EXAONE4_AVAILABLE:
|
||||
num_hidden_layers=4,
|
||||
num_key_value_heads=2,
|
||||
rms_norm_eps=1e-5,
|
||||
rope_theta=1000000.0,
|
||||
tie_word_embeddings=True,
|
||||
use_cache=True,
|
||||
vocab_size=32000,
|
||||
attn_implementation="sdpa",
|
||||
pad_token_id=None,
|
||||
),
|
||||
)
|
||||
|
||||
@@ -1602,12 +1571,12 @@ def run_mini_model(
|
||||
"model_name, num_steps, lr, dtype, loss_atol, loss_rtol, logprobs_atol, logprobs_rtol, param_atol, param_rtol",
|
||||
[
|
||||
pytest.param(
|
||||
"mini_llama4",
|
||||
"mini_llama4", # llama4 requires slightly larger tolerances to pass this test after bug fix to llama4 in transformers v5.0.0
|
||||
32,
|
||||
1e-5,
|
||||
torch.bfloat16,
|
||||
1e-2,
|
||||
5e-2,
|
||||
4e-1,
|
||||
1e-1,
|
||||
1e-1,
|
||||
1e-2,
|
||||
@@ -1618,6 +1587,10 @@ def run_mini_model(
|
||||
not LLAMA4_AVAILABLE,
|
||||
reason="Llama not available in this version of transformers",
|
||||
),
|
||||
pytest.mark.skipif(
|
||||
not IS_TRANSFORMERS_V5_OR_LATER,
|
||||
reason="The `attention_bias` configuration of Llama4 is not set in Transformers v4",
|
||||
),
|
||||
],
|
||||
),
|
||||
pytest.param(
|
||||
@@ -1728,14 +1701,14 @@ def run_mini_model(
|
||||
),
|
||||
# TODO(tcc): Investigate qwen3_moe on different machines.
|
||||
# The loss diverges on ci test (A10G), but it never diverges on my local machine (3080).
|
||||
# Qwen3_moe can pass float32 tests.
|
||||
# Qwen3_moe can pass float32 tests. (mecoli1219): diverges on h100
|
||||
pytest.param(
|
||||
"mini_qwen3_moe",
|
||||
32,
|
||||
1e-5,
|
||||
torch.bfloat16,
|
||||
5e-2,
|
||||
5e-2,
|
||||
2e-1,
|
||||
1e-1, # 1e-1
|
||||
1e-1, # 1e-2
|
||||
1e-2,
|
||||
@@ -1830,9 +1803,9 @@ def run_mini_model(
|
||||
1e-5,
|
||||
torch.bfloat16,
|
||||
5e-2,
|
||||
5e-2,
|
||||
1e-1,
|
||||
1e-2,
|
||||
1e-1,
|
||||
5e-2,
|
||||
1e-2,
|
||||
1e-2,
|
||||
marks=[
|
||||
@@ -1869,10 +1842,6 @@ def run_mini_model(
|
||||
1e-2,
|
||||
marks=[
|
||||
pytest.mark.skipif(not supports_bfloat16(), reason="bfloat16 not supported on this GPU"),
|
||||
pytest.mark.skipif(
|
||||
version.parse(transformers.__version__) < version.parse("4.49.0"),
|
||||
reason="Mistral not available in transformers<=4.49.0",
|
||||
),
|
||||
],
|
||||
),
|
||||
pytest.param(
|
||||
|
||||
@@ -4,11 +4,12 @@ import os
|
||||
os.environ["CUBLAS_WORKSPACE_CONFIG"] = ":4096:8" # Ensure deterministic behavior with CuBLAS
|
||||
import pytest
|
||||
import torch
|
||||
import transformers
|
||||
|
||||
from datasets import load_dataset
|
||||
from packaging import version
|
||||
from torch.utils.data import DataLoader
|
||||
from transformers import PreTrainedTokenizerFast
|
||||
from transformers.models.gemma.tokenization_gemma_fast import GemmaTokenizerFast
|
||||
from transformers.models.siglip.configuration_siglip import SiglipVisionConfig
|
||||
|
||||
from liger_kernel.transformers import apply_liger_kernel_to_gemma3
|
||||
@@ -22,6 +23,7 @@ from liger_kernel.transformers import apply_liger_kernel_to_qwen2_vl
|
||||
from liger_kernel.transformers import apply_liger_kernel_to_qwen3_vl
|
||||
from liger_kernel.transformers import apply_liger_kernel_to_qwen3_vl_moe
|
||||
from liger_kernel.transformers import apply_liger_kernel_to_smolvlm
|
||||
from liger_kernel.utils import infer_device
|
||||
from test.utils import FAKE_CONFIGS_PATH
|
||||
from test.utils import UNTOKENIZED_DATASET_PATH
|
||||
from test.utils import MiniModelConfig
|
||||
@@ -49,12 +51,23 @@ from test.utils import set_seed
|
||||
from test.utils import supports_bfloat16
|
||||
from test.utils import train_bpe_tokenizer
|
||||
|
||||
IS_TRANSFORMERS_V5_OR_LATER = version.parse(transformers.__version__) >= version.parse("5.0.0")
|
||||
|
||||
if IS_TRANSFORMERS_V5_OR_LATER:
|
||||
from transformers.models.gemma.tokenization_gemma import GemmaTokenizer
|
||||
else:
|
||||
from transformers.models.gemma.tokenization_gemma_fast import GemmaTokenizerFast as GemmaTokenizer
|
||||
|
||||
try:
|
||||
# Qwen2-VL is only available in transformers>=4.52.4
|
||||
import transformers
|
||||
|
||||
from packaging import version
|
||||
from transformers.models.qwen2.tokenization_qwen2_fast import Qwen2TokenizerFast
|
||||
|
||||
if IS_TRANSFORMERS_V5_OR_LATER:
|
||||
from transformers.models.qwen2.tokenization_qwen2 import Qwen2Tokenizer
|
||||
else:
|
||||
from transformers.models.qwen2.tokenization_qwen2_fast import Qwen2TokenizerFast as Qwen2Tokenizer
|
||||
from transformers.models.qwen2_vl.configuration_qwen2_vl import Qwen2VLConfig
|
||||
from transformers.models.qwen2_vl.image_processing_qwen2_vl import Qwen2VLImageProcessor
|
||||
from transformers.models.qwen2_vl.modeling_qwen2_vl import Qwen2VLForConditionalGeneration
|
||||
@@ -70,7 +83,11 @@ try:
|
||||
import transformers
|
||||
|
||||
from packaging import version
|
||||
from transformers.models.qwen2.tokenization_qwen2_fast import Qwen2TokenizerFast
|
||||
|
||||
if IS_TRANSFORMERS_V5_OR_LATER:
|
||||
from transformers.models.qwen2.tokenization_qwen2 import Qwen2Tokenizer
|
||||
else:
|
||||
from transformers.models.qwen2.tokenization_qwen2_fast import Qwen2TokenizerFast as Qwen2Tokenizer
|
||||
from transformers.models.qwen2_5_vl.configuration_qwen2_5_vl import Qwen2_5_VLConfig
|
||||
from transformers.models.qwen2_5_vl.modeling_qwen2_5_vl import Qwen2_5_VLForConditionalGeneration
|
||||
from transformers.models.qwen2_5_vl.processing_qwen2_5_vl import Qwen2_5_VLProcessor
|
||||
@@ -82,7 +99,10 @@ except ImportError:
|
||||
QWEN2_5_VL_AVAILABLE = False
|
||||
|
||||
try:
|
||||
from transformers.models.qwen2.tokenization_qwen2_fast import Qwen2TokenizerFast
|
||||
if IS_TRANSFORMERS_V5_OR_LATER:
|
||||
from transformers.models.qwen2.tokenization_qwen2 import Qwen2Tokenizer
|
||||
else:
|
||||
from transformers.models.qwen2.tokenization_qwen2_fast import Qwen2TokenizerFast as Qwen2Tokenizer
|
||||
from transformers.models.qwen2_vl.image_processing_qwen2_vl import Qwen2VLImageProcessor
|
||||
from transformers.models.qwen3_vl.configuration_qwen3_vl import Qwen3VLConfig
|
||||
from transformers.models.qwen3_vl.configuration_qwen3_vl import Qwen3VLTextConfig
|
||||
@@ -138,7 +158,6 @@ try:
|
||||
|
||||
from packaging import version
|
||||
from transformers.models.gemma.configuration_gemma import GemmaConfig
|
||||
from transformers.models.gemma.tokenization_gemma_fast import GemmaTokenizerFast
|
||||
from transformers.models.gemma2.configuration_gemma2 import Gemma2Config
|
||||
from transformers.models.paligemma.configuration_paligemma import PaliGemmaConfig
|
||||
from transformers.models.paligemma.modeling_paligemma import PaliGemmaForConditionalGeneration
|
||||
@@ -146,7 +165,7 @@ try:
|
||||
from transformers.models.siglip.configuration_siglip import SiglipVisionConfig
|
||||
from transformers.models.siglip.image_processing_siglip import SiglipImageProcessor
|
||||
|
||||
PALIGEMMA_AVAILABLE = version.parse(transformers.__version__) >= version.parse("4.46.0")
|
||||
PALIGEMMA_AVAILABLE = True
|
||||
except ImportError:
|
||||
PALIGEMMA_AVAILABLE = False
|
||||
|
||||
@@ -177,7 +196,6 @@ except ImportError:
|
||||
LLAMA4_AVAILABLE = False
|
||||
|
||||
try:
|
||||
# InternVL is only available in transformers>=4.52.1
|
||||
from transformers.models.got_ocr2.image_processing_got_ocr2_fast import GotOcr2ImageProcessorFast
|
||||
from transformers.models.internvl.configuration_internvl import InternVLConfig
|
||||
from transformers.models.internvl.modeling_internvl import InternVLForConditionalGeneration
|
||||
@@ -185,13 +203,14 @@ try:
|
||||
from transformers.models.internvl.video_processing_internvl import InternVLVideoProcessor
|
||||
from transformers.models.qwen2.configuration_qwen2 import Qwen2Config
|
||||
|
||||
INTERNVL_AVAILABLE = True
|
||||
# Input fp32 with bf16 CNN-based models in InternVL is only working in transformers>=4.56.0
|
||||
INTERNVL_AVAILABLE = version.parse(transformers.__version__) >= version.parse("4.56.0")
|
||||
except ImportError:
|
||||
INTERNVL_AVAILABLE = False
|
||||
|
||||
try:
|
||||
# SmolVLM2 is only available in transformers>=4.50.0
|
||||
from transformers.models.gpt2.tokenization_gpt2_fast import GPT2TokenizerFast
|
||||
from transformers.models.gpt2.tokenization_gpt2 import GPT2Tokenizer
|
||||
from transformers.models.smolvlm.configuration_smolvlm import SmolVLMConfig
|
||||
from transformers.models.smolvlm.image_processing_smolvlm import SmolVLMImageProcessor
|
||||
from transformers.models.smolvlm.modeling_smolvlm import SmolVLMForConditionalGeneration
|
||||
@@ -209,7 +228,6 @@ try:
|
||||
except ImportError:
|
||||
NUM2WORDS_AVAILABLE = False
|
||||
|
||||
from liger_kernel.utils import infer_device
|
||||
|
||||
device = infer_device()
|
||||
|
||||
@@ -268,12 +286,12 @@ if LLAMA4_AVAILABLE:
|
||||
num_hidden_layers=4, # 40
|
||||
num_key_value_heads=2, # 8
|
||||
rms_norm_eps=1e-5,
|
||||
rope_theta=500_000,
|
||||
tie_word_embeddings=False,
|
||||
use_cache=True,
|
||||
vocab_size=32000, # 128256,
|
||||
),
|
||||
attn_implementation="sdpa",
|
||||
pad_token_id=None,
|
||||
),
|
||||
)
|
||||
|
||||
@@ -321,8 +339,9 @@ if MLLAMA_AVAILABLE:
|
||||
low_freq_factor=1.0,
|
||||
original_max_position_embeddings=8192,
|
||||
rope_type="llama3",
|
||||
),
|
||||
rope_theta=500_000,
|
||||
)
|
||||
if not IS_TRANSFORMERS_V5_OR_LATER
|
||||
else None,
|
||||
tie_word_embeddings=False,
|
||||
use_cache=True,
|
||||
vocab_size=32000, # 128256,
|
||||
@@ -372,7 +391,6 @@ if PALIGEMMA_AVAILABLE:
|
||||
bos_token_id=1, # 128000
|
||||
eos_token_id=2, # 128001
|
||||
tie_word_embeddings=True,
|
||||
rope_theta=10000.0,
|
||||
attention_bias=False,
|
||||
attention_dropout=0.0,
|
||||
),
|
||||
@@ -421,7 +439,6 @@ if PALIGEMMA_AVAILABLE:
|
||||
bos_token_id=1, # 128000
|
||||
eos_token_id=2, # 128001
|
||||
tie_word_embeddings=True,
|
||||
rope_theta=10000.0,
|
||||
attention_bias=False,
|
||||
attention_dropout=0.0,
|
||||
),
|
||||
@@ -466,7 +483,6 @@ if GEMMA3_AVAILABLE:
|
||||
rms_norm_eps=1e-06,
|
||||
use_cache=True,
|
||||
tie_word_embeddings=True,
|
||||
rope_theta=10000.0,
|
||||
attention_bias=False,
|
||||
attention_dropout=0.0,
|
||||
).to_dict(),
|
||||
@@ -503,10 +519,10 @@ if QWEN2_VL_AVAILABLE:
|
||||
num_hidden_layers=4, # 80
|
||||
num_key_value_heads=2, # 8
|
||||
rms_norm_eps=1e-6, # 1e-5
|
||||
rope_theta=1000000.0,
|
||||
rope_scaling=dict(
|
||||
type="mrope",
|
||||
mrope_section=[16, 24, 24], # (temporal, height, width)
|
||||
**(
|
||||
dict(rope_parameters=dict(mrope_section=[16, 24, 24])) # (temporal, height, width)
|
||||
if IS_TRANSFORMERS_V5_OR_LATER
|
||||
else dict(rope_scaling=dict(type="mrope", mrope_section=[16, 24, 24]))
|
||||
),
|
||||
sliding_window=4096,
|
||||
tie_word_embeddings=True,
|
||||
@@ -545,8 +561,6 @@ if LLAVA_AVAILABLE:
|
||||
num_hidden_layers=4,
|
||||
num_key_value_heads=2,
|
||||
pretraining_tp=1,
|
||||
rope_scaling=None,
|
||||
rope_theta=500000.0,
|
||||
tie_word_embeddings=False,
|
||||
use_cache=True,
|
||||
max_position_embeddings=4096, # llava-1.5-7b-hf
|
||||
@@ -637,7 +651,6 @@ if SMOLVLM2_AVAILABLE:
|
||||
num_hidden_layers=4, # 30 -> reduced to 4 for testing
|
||||
num_key_value_heads=3, # 3 for 256M model
|
||||
rms_norm_eps=1e-5,
|
||||
rope_theta=100000,
|
||||
tie_word_embeddings=False,
|
||||
vocab_size=49280,
|
||||
),
|
||||
@@ -680,10 +693,10 @@ if QWEN2_5_VL_AVAILABLE:
|
||||
num_hidden_layers=4, # 80
|
||||
num_key_value_heads=2, # 8
|
||||
rms_norm_eps=1e-6, # 1e-5
|
||||
rope_theta=1000000.0,
|
||||
rope_scaling=dict(
|
||||
type="mrope",
|
||||
mrope_section=[16, 24, 24], # (temporal, height, width)
|
||||
**(
|
||||
dict(rope_parameters=dict(mrope_section=[16, 24, 24])) # (temporal, height, width)
|
||||
if IS_TRANSFORMERS_V5_OR_LATER
|
||||
else dict(rope_scaling=dict(type="mrope", mrope_section=[16, 24, 24]))
|
||||
),
|
||||
sliding_window=4096,
|
||||
tie_word_embeddings=True,
|
||||
@@ -742,11 +755,12 @@ if QWEN3_VL_AVAILABLE:
|
||||
rms_norm_eps=1e-6,
|
||||
use_cache=False,
|
||||
tie_word_embeddings=True,
|
||||
rope_theta=1000000.0,
|
||||
rope_scaling=dict(
|
||||
type="mrope",
|
||||
mrope_section=[16, 24, 24],
|
||||
),
|
||||
mrope_section=[16, 24, 24], # (temporal, height, width)
|
||||
)
|
||||
if not IS_TRANSFORMERS_V5_OR_LATER
|
||||
else None,
|
||||
attention_dropout=0.0,
|
||||
attention_bias=False,
|
||||
).to_dict(),
|
||||
@@ -794,11 +808,12 @@ if QWEN3_VL_MOE_AVAILABLE:
|
||||
rms_norm_eps=1e-6,
|
||||
use_cache=False,
|
||||
tie_word_embeddings=True,
|
||||
rope_theta=1000000.0,
|
||||
rope_scaling=dict(
|
||||
type="mrope",
|
||||
mrope_section=[16, 24, 24],
|
||||
),
|
||||
mrope_section=[16, 24, 24], # (temporal, height, width)
|
||||
)
|
||||
if not IS_TRANSFORMERS_V5_OR_LATER
|
||||
else None,
|
||||
attention_dropout=0.0,
|
||||
attention_bias=False,
|
||||
decoder_sparse_step=1,
|
||||
@@ -806,6 +821,7 @@ if QWEN3_VL_MOE_AVAILABLE:
|
||||
num_experts_per_tok=2,
|
||||
num_experts=4,
|
||||
mlp_only_layers=[],
|
||||
pad_token_id=None,
|
||||
).to_dict(),
|
||||
),
|
||||
)
|
||||
@@ -825,7 +841,7 @@ def create_processor(model_name: str):
|
||||
)
|
||||
]
|
||||
)
|
||||
qwen_tokenizer = Qwen2TokenizerFast(tokenizer_object=tokenizer_base, **tokenizer_config)
|
||||
qwen_tokenizer = Qwen2Tokenizer(tokenizer_object=tokenizer_base, **tokenizer_config)
|
||||
image_processor = Qwen2VLImageProcessor()
|
||||
video_processor = Qwen2VLVideoProcessor()
|
||||
return Qwen2VLProcessor(
|
||||
@@ -847,7 +863,7 @@ def create_processor(model_name: str):
|
||||
)
|
||||
]
|
||||
)
|
||||
qwen_tokenizer = Qwen2TokenizerFast(tokenizer_object=tokenizer_base, **tokenizer_config)
|
||||
qwen_tokenizer = Qwen2Tokenizer(tokenizer_object=tokenizer_base, **tokenizer_config)
|
||||
image_processor = Qwen2VLImageProcessor()
|
||||
video_processor = Qwen2VLVideoProcessor()
|
||||
return Qwen2_5_VLProcessor(
|
||||
@@ -869,7 +885,7 @@ def create_processor(model_name: str):
|
||||
)
|
||||
]
|
||||
)
|
||||
qwen_tokenizer = Qwen2TokenizerFast(tokenizer_object=tokenizer_base, **tokenizer_config)
|
||||
qwen_tokenizer = Qwen2Tokenizer(tokenizer_object=tokenizer_base, **tokenizer_config)
|
||||
image_processor = Qwen2VLImageProcessor(patch_size=16, temporal_patch_size=2, merge_size=2)
|
||||
video_processor = Qwen3VLVideoProcessor()
|
||||
return Qwen3VLProcessor(
|
||||
@@ -926,7 +942,7 @@ def create_processor(model_name: str):
|
||||
)
|
||||
]
|
||||
)
|
||||
qwen_tokenizer = Qwen2TokenizerFast(tokenizer_object=tokenizer_base, **tokenizer_config)
|
||||
qwen_tokenizer = Qwen2Tokenizer(tokenizer_object=tokenizer_base, **tokenizer_config)
|
||||
image_processor = GotOcr2ImageProcessorFast(
|
||||
crop_to_patches=False, min_patches=1, max_patches=12, size={"height": 448, "width": 448}
|
||||
)
|
||||
@@ -950,7 +966,7 @@ def create_processor(model_name: str):
|
||||
)
|
||||
]
|
||||
)
|
||||
gpt2_tokenizer = GPT2TokenizerFast(tokenizer_object=tokenizer_base, **tokenizer_config)
|
||||
gpt2_tokenizer = GPT2Tokenizer(tokenizer_object=tokenizer_base, **tokenizer_config)
|
||||
image_processor = SmolVLMImageProcessor(size={"longest_edge": 512})
|
||||
video_processor = SmolVLMVideoProcessor()
|
||||
|
||||
@@ -1020,7 +1036,7 @@ def create_processor(model_name: str):
|
||||
]
|
||||
)
|
||||
|
||||
fast_tokenizer = GemmaTokenizerFast(tokenizer_object=tokenizer_base, **tokenizer_config)
|
||||
fast_tokenizer = GemmaTokenizer(tokenizer_object=tokenizer_base, **tokenizer_config)
|
||||
image_processor = SiglipImageProcessor(size={"height": 224, "width": 224}, image_seq_length=256)
|
||||
return PaliGemmaProcessor(image_processor=image_processor, tokenizer=fast_tokenizer)
|
||||
|
||||
@@ -1040,7 +1056,7 @@ def create_processor(model_name: str):
|
||||
)
|
||||
]
|
||||
)
|
||||
fast_tokenizer = GemmaTokenizerFast(tokenizer_object=tokenizer_base, **tokenizer_config)
|
||||
fast_tokenizer = GemmaTokenizer(tokenizer_object=tokenizer_base, **tokenizer_config)
|
||||
image_processor = Gemma3ImageProcessor()
|
||||
return Gemma3Processor(image_processor=image_processor, tokenizer=fast_tokenizer)
|
||||
|
||||
@@ -1402,6 +1418,11 @@ def run_mini_model_multimodal(
|
||||
not LLAMA4_AVAILABLE,
|
||||
reason="Llama4 not available in this version of transformers",
|
||||
),
|
||||
# TODO: Remove this skipif when the bug fix is released in Transformers
|
||||
pytest.mark.skipif(
|
||||
version.parse(transformers.__version__) <= version.parse("5.1.0"),
|
||||
reason="Wait for this bug fix to be released in Transformers: https://github.com/huggingface/transformers/pull/43882",
|
||||
),
|
||||
],
|
||||
),
|
||||
pytest.param(
|
||||
|
||||
@@ -4,8 +4,10 @@ os.environ["CUBLAS_WORKSPACE_CONFIG"] = ":4096:8" # Ensure deterministic behavi
|
||||
|
||||
import pytest
|
||||
import torch
|
||||
import transformers
|
||||
|
||||
from datasets import load_from_disk
|
||||
from packaging import version
|
||||
from torch.utils.data import DataLoader
|
||||
from transformers.models.gemma import GemmaConfig
|
||||
from transformers.models.gemma import GemmaForCausalLM
|
||||
@@ -52,6 +54,7 @@ from liger_kernel.transformers import apply_liger_kernel_to_qwen3_next
|
||||
from liger_kernel.transformers import apply_liger_kernel_to_qwen3_vl
|
||||
from liger_kernel.transformers import apply_liger_kernel_to_qwen3_vl_moe
|
||||
from liger_kernel.transformers import apply_liger_kernel_to_smollm3
|
||||
from liger_kernel.utils import infer_device
|
||||
from test.utils import DEFAULT_DATASET_PATH
|
||||
from test.utils import MiniModelConfig
|
||||
from test.utils import assert_verbose_allclose
|
||||
@@ -92,6 +95,8 @@ from test.utils import set_seed
|
||||
from test.utils import simple_collate_fn
|
||||
from test.utils import supports_bfloat16
|
||||
|
||||
IS_TRANSFORMERS_V5_OR_LATER = version.parse(transformers.__version__) >= version.parse("5.0.0")
|
||||
|
||||
try:
|
||||
from transformers.models.llama4.configuration_llama4 import Llama4TextConfig
|
||||
from transformers.models.llama4.modeling_llama4 import Llama4ForCausalLM
|
||||
@@ -289,8 +294,6 @@ except ImportError:
|
||||
EXAONE4_AVAILABLE = False
|
||||
|
||||
|
||||
from liger_kernel.utils import infer_device
|
||||
|
||||
device = infer_device()
|
||||
|
||||
MINI_MODEL_SETUPS = {
|
||||
@@ -315,8 +318,6 @@ MINI_MODEL_SETUPS = {
|
||||
num_key_value_heads=2, # 8
|
||||
pretraining_tp=1,
|
||||
rms_norm_eps=1e-5,
|
||||
rope_scaling=None,
|
||||
rope_theta=500000.0,
|
||||
tie_word_embeddings=False,
|
||||
use_cache=True,
|
||||
vocab_size=32000, # 128256,
|
||||
@@ -344,7 +345,6 @@ MINI_MODEL_SETUPS = {
|
||||
num_hidden_layers=4,
|
||||
num_key_value_heads=2,
|
||||
rms_norm_eps=1e-6,
|
||||
rope_theta=1000000.0,
|
||||
sliding_window=131072,
|
||||
tie_word_embeddings=True,
|
||||
use_cache=True,
|
||||
@@ -373,7 +373,6 @@ MINI_MODEL_SETUPS = {
|
||||
num_hidden_layers=4, # 32
|
||||
num_key_value_heads=None, # defaults to num_attention_heads
|
||||
rms_norm_eps=1e-5,
|
||||
rope_theta=10000.0,
|
||||
sliding_window=None,
|
||||
tie_word_embeddings=False,
|
||||
use_cache=True,
|
||||
@@ -398,7 +397,6 @@ MINI_MODEL_SETUPS = {
|
||||
num_hidden_layers=4,
|
||||
num_key_value_heads=2,
|
||||
rms_norm_eps=1e-5,
|
||||
rope_theta=10000.0,
|
||||
sliding_window=4096,
|
||||
tie_word_embeddings=False,
|
||||
use_cache=True,
|
||||
@@ -423,7 +421,6 @@ MINI_MODEL_SETUPS = {
|
||||
num_hidden_layers=4, # 32
|
||||
num_key_value_heads=2, # 8
|
||||
rms_norm_eps=1e-5,
|
||||
rope_theta=10000.0,
|
||||
sliding_window=4096,
|
||||
tie_word_embeddings=False,
|
||||
use_cache=True,
|
||||
@@ -458,7 +455,6 @@ MINI_MODEL_SETUPS = {
|
||||
bos_token_id=1, # 128000
|
||||
eos_token_id=2, # 128001
|
||||
tie_word_embeddings=True,
|
||||
rope_theta=10000.0,
|
||||
attention_bias=False,
|
||||
attention_dropout=0.0,
|
||||
),
|
||||
@@ -486,7 +482,6 @@ MINI_MODEL_SETUPS = {
|
||||
bos_token_id=1, # 128000
|
||||
eos_token_id=2, # 128001
|
||||
tie_word_embeddings=True,
|
||||
rope_theta=10000.0,
|
||||
attention_bias=False,
|
||||
attention_dropout=0.0,
|
||||
),
|
||||
@@ -514,7 +509,6 @@ MINI_MODEL_SETUPS = {
|
||||
bos_token_id=1, # 128000
|
||||
eos_token_id=2, # 128001
|
||||
tie_word_embeddings=True,
|
||||
rope_theta=10000.0,
|
||||
attention_bias=False,
|
||||
attention_dropout=0.0,
|
||||
attn_implementation="eager",
|
||||
@@ -543,8 +537,6 @@ if LLAMA4_AVAILABLE:
|
||||
num_hidden_layers=4, # 61
|
||||
num_key_value_heads=2,
|
||||
rms_norm_eps=1e-5,
|
||||
rope_scaling=None,
|
||||
rope_theta=10000.0,
|
||||
tie_word_embeddings=False,
|
||||
use_cache=True,
|
||||
vocab_size=32000, # 151552
|
||||
@@ -571,7 +563,6 @@ if QWEN3_AVAILABLE:
|
||||
num_hidden_layers=4,
|
||||
num_key_value_heads=2,
|
||||
rms_norm_eps=1e-6,
|
||||
rope_theta=1000000.0,
|
||||
sliding_window=131072,
|
||||
tie_word_embeddings=True,
|
||||
use_cache=True,
|
||||
@@ -597,8 +588,6 @@ if QWEN3_AVAILABLE:
|
||||
rms_norm_eps=1e-6,
|
||||
use_cache=True,
|
||||
tie_word_embeddings=False,
|
||||
rope_theta=10000.0,
|
||||
rope_scaling=None,
|
||||
attention_bias=False,
|
||||
use_sliding_window=False,
|
||||
sliding_window=4096,
|
||||
@@ -642,15 +631,16 @@ if QWEN3_VL_AVAILABLE:
|
||||
num_key_value_heads=2,
|
||||
pad_token_id=2,
|
||||
rms_norm_eps=1e-6,
|
||||
rope_theta=1000000.0,
|
||||
rope_scaling=dict(
|
||||
type="mrope",
|
||||
mrope_section=[16, 24, 24],
|
||||
),
|
||||
sliding_window=131072,
|
||||
tie_word_embeddings=False,
|
||||
use_cache=True,
|
||||
vocab_size=32000,
|
||||
rope_scaling=dict(
|
||||
type="mrope",
|
||||
mrope_section=[16, 24, 24], # (temporal, height, width)
|
||||
)
|
||||
if not IS_TRANSFORMERS_V5_OR_LATER
|
||||
else None,
|
||||
),
|
||||
vision_config=dict(
|
||||
depth=4,
|
||||
@@ -697,11 +687,6 @@ if QWEN3_VL_MOE_AVAILABLE:
|
||||
num_key_value_heads=2,
|
||||
pad_token_id=2,
|
||||
rms_norm_eps=1e-6,
|
||||
rope_theta=1000000.0,
|
||||
rope_scaling=dict(
|
||||
type="mrope",
|
||||
mrope_section=[16, 24, 24],
|
||||
),
|
||||
sliding_window=131072,
|
||||
tie_word_embeddings=False,
|
||||
use_cache=True,
|
||||
@@ -751,7 +736,6 @@ if GEMMA3_AVAILABLE:
|
||||
bos_token_id=2,
|
||||
eos_token_id=1,
|
||||
tie_word_embeddings=True,
|
||||
rope_theta=10000.0, # 1000000
|
||||
attention_bias=False,
|
||||
attention_dropout=0.0,
|
||||
attn_implementation="eager",
|
||||
@@ -778,18 +762,20 @@ if MLLAMA_AVAILABLE:
|
||||
num_hidden_layers=4, # 40
|
||||
num_key_value_heads=2, # 8
|
||||
rms_norm_eps=1e-5,
|
||||
tie_word_embeddings=False,
|
||||
use_cache=True,
|
||||
vocab_size=32000, # 128256,
|
||||
attn_implementation="sdpa", # default value, pytorch native attention
|
||||
rope_scaling=dict(
|
||||
factor=8.0,
|
||||
high_freq_factor=4.0,
|
||||
low_freq_factor=1.0,
|
||||
original_max_position_embeddings=8192,
|
||||
rope_type="llama3",
|
||||
),
|
||||
rope_theta=500_000,
|
||||
tie_word_embeddings=False,
|
||||
use_cache=True,
|
||||
vocab_size=32000, # 128256,
|
||||
attn_implementation="sdpa", # default value, pytorch native attention
|
||||
rope_theta=500_000,
|
||||
)
|
||||
if not IS_TRANSFORMERS_V5_OR_LATER
|
||||
else None,
|
||||
),
|
||||
)
|
||||
|
||||
@@ -819,10 +805,10 @@ if QWEN2_VL_AVAILABLE:
|
||||
num_hidden_layers=4, # 80
|
||||
num_key_value_heads=2, # 8
|
||||
rms_norm_eps=1e-6, # 1e-5
|
||||
rope_theta=1000000.0,
|
||||
rope_scaling=dict(
|
||||
type="mrope",
|
||||
mrope_section=[16, 24, 24], # (temporal, height, width)
|
||||
**(
|
||||
dict(rope_parameters=dict(mrope_section=[16, 24, 24])) # (temporal, height, width)
|
||||
if IS_TRANSFORMERS_V5_OR_LATER
|
||||
else dict(rope_scaling=dict(type="mrope", mrope_section=[16, 24, 24]))
|
||||
),
|
||||
sliding_window=4096,
|
||||
tie_word_embeddings=False,
|
||||
@@ -871,10 +857,10 @@ if QWEN2_5_VL_AVAILABLE:
|
||||
num_hidden_layers=4, # 80
|
||||
num_key_value_heads=2, # 8
|
||||
rms_norm_eps=1e-6, # 1e-5
|
||||
rope_theta=1000000.0,
|
||||
rope_scaling=dict(
|
||||
type="mrope",
|
||||
mrope_section=[16, 24, 24], # (temporal, height, width)
|
||||
**(
|
||||
dict(rope_parameters=dict(mrope_section=[16, 24, 24])) # (temporal, height, width)
|
||||
if IS_TRANSFORMERS_V5_OR_LATER
|
||||
else dict(rope_scaling=dict(type="mrope", mrope_section=[16, 24, 24]))
|
||||
),
|
||||
sliding_window=4096,
|
||||
tie_word_embeddings=False,
|
||||
@@ -923,8 +909,6 @@ if GRANITE_AVAILABLE:
|
||||
num_key_value_heads=2, # 8
|
||||
pretraining_tp=1,
|
||||
rms_norm_eps=1e-5,
|
||||
rope_scaling=None,
|
||||
rope_theta=500000.0,
|
||||
tie_word_embeddings=False,
|
||||
use_cache=True,
|
||||
vocab_size=32000, # 128256,
|
||||
@@ -957,8 +941,6 @@ if LLAVA_AVAILABLE:
|
||||
num_hidden_layers=4,
|
||||
num_key_value_heads=2,
|
||||
pretraining_tp=1,
|
||||
rope_scaling=None,
|
||||
rope_theta=500000.0,
|
||||
tie_word_embeddings=False,
|
||||
use_cache=True,
|
||||
max_position_embeddings=4096, # llava-1.5-7b-hf
|
||||
@@ -1016,8 +998,6 @@ if OLMO2_AVAILABLE:
|
||||
num_hidden_layers=4, # 40
|
||||
num_key_value_heads=2, # 8
|
||||
rms_norm_eps=1e-5,
|
||||
rope_scaling=None,
|
||||
rope_theta=500_000,
|
||||
tie_word_embeddings=False,
|
||||
use_cache=True,
|
||||
vocab_size=32000, # 128256,
|
||||
@@ -1045,8 +1025,6 @@ if OLMO3_AVAILABLE:
|
||||
num_hidden_layers=4, # 40
|
||||
num_key_value_heads=2, # 8
|
||||
rms_norm_eps=1e-5,
|
||||
rope_scaling=None,
|
||||
rope_theta=500_000,
|
||||
tie_word_embeddings=False,
|
||||
use_cache=True,
|
||||
vocab_size=32000, # 128256,
|
||||
@@ -1075,8 +1053,6 @@ if GLM4_AVAILABLE:
|
||||
num_hidden_layers=4, # 61
|
||||
num_key_value_heads=2,
|
||||
rms_norm_eps=1e-5,
|
||||
rope_scaling=None,
|
||||
rope_theta=500_000,
|
||||
tie_word_embeddings=False,
|
||||
use_cache=True,
|
||||
vocab_size=32000, # 151552
|
||||
@@ -1111,8 +1087,6 @@ if GLM4V_AVAILABLE:
|
||||
num_hidden_layers=4, # 61
|
||||
num_key_value_heads=2,
|
||||
rms_norm_eps=1e-5,
|
||||
rope_scaling=None,
|
||||
rope_theta=500_000,
|
||||
tie_word_embeddings=False,
|
||||
use_cache=True,
|
||||
vocab_size=32000, # 151552
|
||||
@@ -1128,13 +1102,14 @@ if GLM4V_AVAILABLE:
|
||||
"num_hidden_layers": 4,
|
||||
"num_key_value_heads": 2,
|
||||
"rms_norm_eps": 1e-5,
|
||||
"rope_scaling": {
|
||||
"type": "default",
|
||||
"mrope_section": [8, 12, 12], # (temporal, height, width)
|
||||
},
|
||||
"rope_theta": 500_000,
|
||||
"vocab_size": 32000,
|
||||
"attention_bias": True,
|
||||
**(
|
||||
{"rope_scaling": {"type": "default", "mrope_section": [8, 12, 12]}}
|
||||
if not IS_TRANSFORMERS_V5_OR_LATER
|
||||
else {}
|
||||
),
|
||||
"pad_token_id": None,
|
||||
},
|
||||
vision_config={
|
||||
"depth": 4, # 32
|
||||
@@ -1178,8 +1153,6 @@ if GLM4V_MOE_AVAILABLE:
|
||||
num_hidden_layers=4, # 61
|
||||
num_key_value_heads=2,
|
||||
rms_norm_eps=1e-5,
|
||||
rope_scaling=None,
|
||||
rope_theta=500_000,
|
||||
tie_word_embeddings=False,
|
||||
use_cache=True,
|
||||
vocab_size=32000, # 151552
|
||||
@@ -1195,11 +1168,6 @@ if GLM4V_MOE_AVAILABLE:
|
||||
"num_hidden_layers": 4,
|
||||
"num_key_value_heads": 2,
|
||||
"rms_norm_eps": 1e-5,
|
||||
"rope_scaling": {
|
||||
"type": "default",
|
||||
"mrope_section": [8, 12, 12], # (temporal, height, width)
|
||||
},
|
||||
"rope_theta": 500_000,
|
||||
"vocab_size": 32000,
|
||||
"attention_bias": True,
|
||||
"attention_dropout": 0.0,
|
||||
@@ -1212,6 +1180,11 @@ if GLM4V_MOE_AVAILABLE:
|
||||
"topk_group": 1,
|
||||
"first_k_dense_replace": 1,
|
||||
"norm_topk_prob": True,
|
||||
**(
|
||||
{"rope_scaling": {"type": "default", "mrope_section": [8, 12, 12]}}
|
||||
if not IS_TRANSFORMERS_V5_OR_LATER
|
||||
else {}
|
||||
),
|
||||
},
|
||||
vision_config={
|
||||
"depth": 4, # 32
|
||||
@@ -1249,8 +1222,6 @@ if SMOLLM3_AVAILABLE:
|
||||
num_key_value_heads=2, # 8
|
||||
pretraining_tp=1,
|
||||
rms_norm_eps=1e-5,
|
||||
rope_scaling=None,
|
||||
rope_theta=500000.0,
|
||||
tie_word_embeddings=False,
|
||||
use_cache=True,
|
||||
vocab_size=32000, # 128256,
|
||||
@@ -1341,8 +1312,6 @@ if QWEN3NEXT_AVAILABLE:
|
||||
rms_norm_eps=1e-6,
|
||||
use_cache=True,
|
||||
tie_word_embeddings=False,
|
||||
rope_theta=10000.0,
|
||||
rope_scaling=None,
|
||||
attention_bias=False,
|
||||
use_sliding_window=False,
|
||||
sliding_window=4096,
|
||||
@@ -1383,7 +1352,6 @@ if HUNYUAN_V1_AVAILABLE:
|
||||
initializer_range=0.02,
|
||||
norm_eps=1e-6,
|
||||
num_key_value_heads=2,
|
||||
rope_theta=10000.0,
|
||||
partial_rotary_factor=1.0,
|
||||
vocab_size=32000,
|
||||
use_cache=True,
|
||||
@@ -1414,8 +1382,6 @@ if HUNYUAN_V1_AVAILABLE:
|
||||
eod_token_id=3,
|
||||
sep_token_id=4,
|
||||
tie_word_embeddings=False,
|
||||
rope_theta=10000.0,
|
||||
rope_scaling=None,
|
||||
attention_bias=False,
|
||||
attention_dropout=0.0,
|
||||
num_experts=2,
|
||||
@@ -1442,11 +1408,11 @@ if EXAONE4_AVAILABLE:
|
||||
num_hidden_layers=4,
|
||||
num_key_value_heads=2,
|
||||
rms_norm_eps=1e-5,
|
||||
rope_theta=1000000.0,
|
||||
tie_word_embeddings=True,
|
||||
use_cache=True,
|
||||
vocab_size=32000,
|
||||
attn_implementation="sdpa",
|
||||
pad_token_id=None,
|
||||
),
|
||||
)
|
||||
|
||||
@@ -1540,12 +1506,12 @@ def run_mini_model(
|
||||
[
|
||||
# Tolerance is set higher than usual to pass the tests.
|
||||
pytest.param(
|
||||
"mini_llama4",
|
||||
"mini_llama4", # llama4 requires slightly larger tolerances to pass this test after bug fix to llama4 in transformers v5.0.0
|
||||
32,
|
||||
1e-5,
|
||||
torch.bfloat16,
|
||||
1e-2,
|
||||
5e-2,
|
||||
4e-1,
|
||||
3e-1,
|
||||
2e-1,
|
||||
1e-2,
|
||||
@@ -1666,7 +1632,7 @@ def run_mini_model(
|
||||
1e-5,
|
||||
torch.bfloat16,
|
||||
1e-2,
|
||||
5e-2,
|
||||
2e-1,
|
||||
1e-1,
|
||||
1e-2,
|
||||
1e-2,
|
||||
|
||||
@@ -4,8 +4,10 @@ os.environ["CUBLAS_WORKSPACE_CONFIG"] = ":4096:8" # Ensure deterministic behavi
|
||||
|
||||
import pytest
|
||||
import torch
|
||||
import transformers
|
||||
|
||||
from datasets import load_from_disk
|
||||
from packaging import version
|
||||
from torch.utils.data import DataLoader
|
||||
from transformers.models.gemma import GemmaConfig
|
||||
from transformers.models.gemma import GemmaForCausalLM
|
||||
@@ -53,6 +55,7 @@ from liger_kernel.transformers import apply_liger_kernel_to_qwen3_next
|
||||
from liger_kernel.transformers import apply_liger_kernel_to_qwen3_vl
|
||||
from liger_kernel.transformers import apply_liger_kernel_to_qwen3_vl_moe
|
||||
from liger_kernel.transformers import apply_liger_kernel_to_smollm3
|
||||
from liger_kernel.utils import infer_device
|
||||
from test.utils import DEFAULT_DATASET_PATH
|
||||
from test.utils import MiniModelConfig
|
||||
from test.utils import assert_verbose_allclose
|
||||
@@ -93,6 +96,8 @@ from test.utils import revert_liger_kernel_to_smollm3
|
||||
from test.utils import set_seed
|
||||
from test.utils import simple_collate_fn
|
||||
|
||||
IS_TRANSFORMERS_V5_OR_LATER = version.parse(transformers.__version__) >= version.parse("5.0.0")
|
||||
|
||||
try:
|
||||
from transformers.models.llama4.configuration_llama4 import Llama4TextConfig
|
||||
from transformers.models.llama4.modeling_llama4 import Llama4ForCausalLM
|
||||
@@ -306,8 +311,6 @@ except ImportError:
|
||||
EXAONE4_AVAILABLE = False
|
||||
|
||||
|
||||
from liger_kernel.utils import infer_device
|
||||
|
||||
device = infer_device()
|
||||
|
||||
MINI_MODEL_SETUPS = {
|
||||
@@ -332,8 +335,6 @@ MINI_MODEL_SETUPS = {
|
||||
num_key_value_heads=2, # 8
|
||||
pretraining_tp=1,
|
||||
rms_norm_eps=1e-5,
|
||||
rope_scaling=None,
|
||||
rope_theta=500000.0,
|
||||
tie_word_embeddings=False,
|
||||
use_cache=True,
|
||||
vocab_size=32000, # 128256,
|
||||
@@ -361,7 +362,6 @@ MINI_MODEL_SETUPS = {
|
||||
num_hidden_layers=4,
|
||||
num_key_value_heads=2,
|
||||
rms_norm_eps=1e-6,
|
||||
rope_theta=1000000.0,
|
||||
sliding_window=131072,
|
||||
tie_word_embeddings=True,
|
||||
use_cache=True,
|
||||
@@ -390,7 +390,6 @@ MINI_MODEL_SETUPS = {
|
||||
num_hidden_layers=4, # 32
|
||||
num_key_value_heads=None, # defaults to num_attention_heads
|
||||
rms_norm_eps=1e-5,
|
||||
rope_theta=10000.0,
|
||||
sliding_window=None,
|
||||
tie_word_embeddings=False,
|
||||
use_cache=True,
|
||||
@@ -415,7 +414,6 @@ MINI_MODEL_SETUPS = {
|
||||
num_hidden_layers=4,
|
||||
num_key_value_heads=2,
|
||||
rms_norm_eps=1e-5,
|
||||
rope_theta=10000.0,
|
||||
sliding_window=4096,
|
||||
tie_word_embeddings=False,
|
||||
use_cache=True,
|
||||
@@ -440,7 +438,6 @@ MINI_MODEL_SETUPS = {
|
||||
num_hidden_layers=4, # 32
|
||||
num_key_value_heads=2, # 8
|
||||
rms_norm_eps=1e-5,
|
||||
rope_theta=10000.0,
|
||||
sliding_window=4096,
|
||||
tie_word_embeddings=False,
|
||||
use_cache=True,
|
||||
@@ -475,7 +472,6 @@ MINI_MODEL_SETUPS = {
|
||||
bos_token_id=1, # 128000
|
||||
eos_token_id=2, # 128001
|
||||
tie_word_embeddings=True,
|
||||
rope_theta=10000.0,
|
||||
attention_bias=False,
|
||||
attention_dropout=0.0,
|
||||
),
|
||||
@@ -503,7 +499,6 @@ MINI_MODEL_SETUPS = {
|
||||
bos_token_id=1, # 128000
|
||||
eos_token_id=2, # 128001
|
||||
tie_word_embeddings=True,
|
||||
rope_theta=10000.0,
|
||||
attention_bias=False,
|
||||
attention_dropout=0.0,
|
||||
),
|
||||
@@ -531,7 +526,6 @@ MINI_MODEL_SETUPS = {
|
||||
bos_token_id=1, # 128000
|
||||
eos_token_id=2, # 128001
|
||||
tie_word_embeddings=True,
|
||||
rope_theta=10000.0,
|
||||
attention_bias=False,
|
||||
attention_dropout=0.0,
|
||||
attn_implementation="eager",
|
||||
@@ -559,8 +553,6 @@ if LLAMA4_AVAILABLE:
|
||||
num_hidden_layers=4, # 61
|
||||
num_key_value_heads=2,
|
||||
rms_norm_eps=1e-5,
|
||||
rope_scaling=None,
|
||||
rope_theta=10000.0,
|
||||
tie_word_embeddings=False,
|
||||
use_cache=True,
|
||||
vocab_size=32000, # 151552
|
||||
@@ -588,7 +580,6 @@ if QWEN3_AVAILABLE:
|
||||
num_hidden_layers=4,
|
||||
num_key_value_heads=2,
|
||||
rms_norm_eps=1e-6,
|
||||
rope_theta=1000000.0,
|
||||
sliding_window=131072,
|
||||
tie_word_embeddings=True,
|
||||
use_cache=True,
|
||||
@@ -614,8 +605,6 @@ if QWEN3_AVAILABLE:
|
||||
rms_norm_eps=1e-6,
|
||||
use_cache=True,
|
||||
tie_word_embeddings=False,
|
||||
rope_theta=10000.0,
|
||||
rope_scaling=None,
|
||||
attention_bias=False,
|
||||
use_sliding_window=False,
|
||||
sliding_window=4096,
|
||||
@@ -651,14 +640,6 @@ if GPT_OSS_AVAILABLE:
|
||||
rms_norm_eps=1e-5,
|
||||
use_cache=True,
|
||||
tie_word_embeddings=False,
|
||||
rope_parameters={
|
||||
"rope_type": "yarn",
|
||||
"factor": 8.0,
|
||||
"beta_fast": 32.0,
|
||||
"beta_slow": 1.0,
|
||||
"truncate": False,
|
||||
"original_max_position_embeddings": 4096,
|
||||
},
|
||||
attention_dropout=0.0,
|
||||
num_local_experts=8, # Reduced from 32 for mini model
|
||||
num_experts_per_tok=2, # Reduced from 4 for mini model
|
||||
@@ -691,7 +672,6 @@ if GEMMA3_AVAILABLE:
|
||||
bos_token_id=2,
|
||||
eos_token_id=1,
|
||||
tie_word_embeddings=True,
|
||||
rope_theta=10000.0, # 1000000
|
||||
attention_bias=False,
|
||||
attention_dropout=0.0,
|
||||
attn_implementation="eager",
|
||||
@@ -718,18 +698,20 @@ if MLLAMA_AVAILABLE:
|
||||
num_hidden_layers=4, # 40
|
||||
num_key_value_heads=2, # 8
|
||||
rms_norm_eps=1e-5,
|
||||
tie_word_embeddings=False,
|
||||
use_cache=True,
|
||||
vocab_size=32000, # 128256,
|
||||
attn_implementation="sdpa", # default value, pytorch native attention
|
||||
rope_scaling=dict(
|
||||
factor=8.0,
|
||||
high_freq_factor=4.0,
|
||||
low_freq_factor=1.0,
|
||||
original_max_position_embeddings=8192,
|
||||
rope_type="llama3",
|
||||
),
|
||||
rope_theta=500_000,
|
||||
tie_word_embeddings=False,
|
||||
use_cache=True,
|
||||
vocab_size=32000, # 128256,
|
||||
attn_implementation="sdpa", # default value, pytorch native attention
|
||||
rope_theta=500_000,
|
||||
)
|
||||
if not IS_TRANSFORMERS_V5_OR_LATER
|
||||
else None,
|
||||
),
|
||||
)
|
||||
|
||||
@@ -739,36 +721,38 @@ if QWEN2_VL_AVAILABLE:
|
||||
liger_kernel_patch_revert_func=revert_liger_kernel_to_qwen2_vl,
|
||||
model_class=Qwen2VLForConditionalGeneration,
|
||||
mini_model_config=Qwen2VLConfig(
|
||||
attention_dropout=0.0,
|
||||
# bos and eos set to match the Mistral-7B tokenizer used to create the test dataset
|
||||
# https://huggingface.co/mistralai/Mistral-7B-v0.1/blob/main/config.json
|
||||
bos_token_id=1, # 151643
|
||||
eos_token_id=2, # 151645
|
||||
# In transformers v5, text-related parameters must be in text_config
|
||||
text_config={
|
||||
"attention_dropout": 0.0,
|
||||
# bos and eos set to match the Mistral-7B tokenizer used to create the test dataset
|
||||
# https://huggingface.co/mistralai/Mistral-7B-v0.1/blob/main/config.json
|
||||
"bos_token_id": 1, # 151643
|
||||
"eos_token_id": 2, # 151645
|
||||
"hidden_act": "silu",
|
||||
"hidden_size": 1536, # 8192
|
||||
"initializer_range": 0.02,
|
||||
"intermediate_size": 4864, # 29568
|
||||
"max_position_embeddings": 32768,
|
||||
"max_window_layers": 4, # 80
|
||||
"num_attention_heads": 12, # 64
|
||||
"num_hidden_layers": 4, # 80
|
||||
"num_key_value_heads": 2, # 8
|
||||
"rms_norm_eps": 1e-6, # 1e-5
|
||||
**(
|
||||
{"rope_parameters": {"mrope_section": [16, 24, 24]}} # (temporal, height, width)
|
||||
if IS_TRANSFORMERS_V5_OR_LATER
|
||||
else {"rope_scaling": {"type": "mrope", "mrope_section": [16, 24, 24]}}
|
||||
),
|
||||
"sliding_window": 4096,
|
||||
"tie_word_embeddings": False,
|
||||
"use_cache": True,
|
||||
"vocab_size": 32768, # 152064 # >32k, Mistral-7B tokenizer vocab size
|
||||
"use_sliding_window": False,
|
||||
},
|
||||
vision_start_token_id=32765, # vocab_size - 5
|
||||
vision_end_token_id=32766, # vocab_size - 4
|
||||
vision_token_id=32767, # vocab_size - 3
|
||||
image_token_id=32768, # vocab_size - 2
|
||||
video_token_id=32769, # vocab_size - 1
|
||||
hidden_act="silu",
|
||||
hidden_size=1536, # 8192
|
||||
initializer_range=0.02,
|
||||
intermediate_size=4864, # 29568
|
||||
max_position_embeddings=32768,
|
||||
max_window_layers=4, # 80
|
||||
num_attention_heads=12, # 64
|
||||
num_hidden_layers=4, # 80
|
||||
num_key_value_heads=2, # 8
|
||||
rms_norm_eps=1e-6, # 1e-5
|
||||
rope_theta=1000000.0,
|
||||
rope_scaling=dict(
|
||||
type="mrope",
|
||||
mrope_section=[16, 24, 24], # (temporal, height, width)
|
||||
),
|
||||
sliding_window=4096,
|
||||
tie_word_embeddings=False,
|
||||
use_cache=True,
|
||||
vocab_size=32768, # 152064 # >32k, Mistral-7B tokenizer vocab size
|
||||
use_sliding_window=False,
|
||||
vision_config={
|
||||
"depth": 4, # 32
|
||||
"embed_dim": 1280,
|
||||
@@ -781,7 +765,6 @@ if QWEN2_VL_AVAILABLE:
|
||||
"spatial_patch_size": 14,
|
||||
"temporal_patch_size": 2,
|
||||
},
|
||||
attn_implementation="sdpa",
|
||||
),
|
||||
)
|
||||
|
||||
@@ -791,36 +774,38 @@ if QWEN2_5_VL_AVAILABLE:
|
||||
liger_kernel_patch_revert_func=revert_liger_kernel_to_qwen2_5_vl,
|
||||
model_class=Qwen2_5_VLForConditionalGeneration,
|
||||
mini_model_config=Qwen2_5_VLConfig(
|
||||
attention_dropout=0.0,
|
||||
# bos and eos set to match the Mistral-7B tokenizer used to create the test dataset
|
||||
# https://huggingface.co/mistralai/Mistral-7B-v0.1/blob/main/config.json
|
||||
bos_token_id=1, # 151643
|
||||
eos_token_id=2, # 151645
|
||||
# In transformers v5, text-related parameters must be in text_config
|
||||
text_config={
|
||||
"attention_dropout": 0.0,
|
||||
# bos and eos set to match the Mistral-7B tokenizer used to create the test dataset
|
||||
# https://huggingface.co/mistralai/Mistral-7B-v0.1/blob/main/config.json
|
||||
"bos_token_id": 1, # 151643
|
||||
"eos_token_id": 2, # 151645
|
||||
"hidden_act": "silu",
|
||||
"hidden_size": 1536, # 8192
|
||||
"initializer_range": 0.02,
|
||||
"intermediate_size": 4864, # 29568
|
||||
"max_position_embeddings": 32768,
|
||||
"max_window_layers": 4, # 80
|
||||
"num_attention_heads": 12, # 64
|
||||
"num_hidden_layers": 4, # 80
|
||||
"num_key_value_heads": 2, # 8
|
||||
"rms_norm_eps": 1e-6, # 1e-5
|
||||
**(
|
||||
{"rope_parameters": {"mrope_section": [16, 24, 24]}} # (temporal, height, width)
|
||||
if IS_TRANSFORMERS_V5_OR_LATER
|
||||
else {"rope_scaling": {"type": "mrope", "mrope_section": [16, 24, 24]}}
|
||||
),
|
||||
"sliding_window": 4096,
|
||||
"tie_word_embeddings": False,
|
||||
"use_cache": True,
|
||||
"vocab_size": 32768, # 152064 # >32k, Mistral-7B tokenizer vocab size
|
||||
"use_sliding_window": False,
|
||||
},
|
||||
vision_start_token_id=32765, # vocab_size - 5
|
||||
vision_end_token_id=32766, # vocab_size - 4
|
||||
vision_token_id=32767, # vocab_size - 3
|
||||
image_token_id=32768, # vocab_size - 2
|
||||
video_token_id=32769, # vocab_size - 1
|
||||
hidden_act="silu",
|
||||
hidden_size=1536, # 8192
|
||||
initializer_range=0.02,
|
||||
intermediate_size=4864, # 29568
|
||||
max_position_embeddings=32768,
|
||||
max_window_layers=4, # 80
|
||||
num_attention_heads=12, # 64
|
||||
num_hidden_layers=4, # 80
|
||||
num_key_value_heads=2, # 8
|
||||
rms_norm_eps=1e-6, # 1e-5
|
||||
rope_theta=1000000.0,
|
||||
rope_scaling=dict(
|
||||
type="mrope",
|
||||
mrope_section=[16, 24, 24], # (temporal, height, width)
|
||||
),
|
||||
sliding_window=4096,
|
||||
tie_word_embeddings=False,
|
||||
use_cache=True,
|
||||
vocab_size=32768, # 152064 # >32k, Mistral-7B tokenizer vocab size
|
||||
use_sliding_window=False,
|
||||
vision_config={
|
||||
"depth": 4, # 32
|
||||
"hidden_act": "silu",
|
||||
@@ -837,7 +822,6 @@ if QWEN2_5_VL_AVAILABLE:
|
||||
"tokens_per_second": 2,
|
||||
"temporal_patch_size": 2,
|
||||
},
|
||||
attn_implementation="sdpa",
|
||||
),
|
||||
)
|
||||
|
||||
@@ -866,13 +850,14 @@ if QWEN3_VL_AVAILABLE:
|
||||
num_hidden_layers=4,
|
||||
num_key_value_heads=2,
|
||||
rms_norm_eps=1e-6,
|
||||
rope_theta=1000000.0,
|
||||
rope_scaling=dict(
|
||||
type="mrope",
|
||||
mrope_section=[16, 24, 24],
|
||||
),
|
||||
use_cache=True,
|
||||
vocab_size=32768,
|
||||
rope_scaling=dict(
|
||||
type="mrope",
|
||||
mrope_section=[16, 24, 24], # (temporal, height, width)
|
||||
)
|
||||
if not IS_TRANSFORMERS_V5_OR_LATER
|
||||
else None,
|
||||
),
|
||||
vision_config=dict(
|
||||
depth=4,
|
||||
@@ -919,11 +904,6 @@ if QWEN3_VL_MOE_AVAILABLE:
|
||||
num_key_value_heads=2,
|
||||
head_dim=128,
|
||||
rms_norm_eps=1e-6,
|
||||
rope_theta=1000000.0,
|
||||
rope_scaling=dict(
|
||||
type="mrope",
|
||||
mrope_section=[16, 24, 24],
|
||||
),
|
||||
use_cache=True,
|
||||
vocab_size=32768,
|
||||
decoder_sparse_step=1,
|
||||
@@ -932,6 +912,13 @@ if QWEN3_VL_MOE_AVAILABLE:
|
||||
num_experts=4,
|
||||
tie_word_embeddings=False,
|
||||
mlp_only_layers=[],
|
||||
pad_token_id=None,
|
||||
rope_scaling=dict(
|
||||
type="mrope",
|
||||
mrope_section=[16, 24, 24], # (temporal, height, width)
|
||||
)
|
||||
if not IS_TRANSFORMERS_V5_OR_LATER
|
||||
else None,
|
||||
).to_dict(),
|
||||
vision_config=Qwen3VLMoeVisionConfig(
|
||||
depth=4,
|
||||
@@ -973,8 +960,6 @@ if GRANITE_AVAILABLE:
|
||||
num_key_value_heads=2, # 8
|
||||
pretraining_tp=1,
|
||||
rms_norm_eps=1e-5,
|
||||
rope_scaling=None,
|
||||
rope_theta=500000.0,
|
||||
tie_word_embeddings=False,
|
||||
use_cache=True,
|
||||
vocab_size=32000, # 128256,
|
||||
@@ -1006,8 +991,6 @@ if OLMO2_AVAILABLE:
|
||||
num_hidden_layers=4, # 40
|
||||
num_key_value_heads=2, # 8
|
||||
rms_norm_eps=1e-5,
|
||||
rope_scaling=None,
|
||||
rope_theta=500_000,
|
||||
tie_word_embeddings=False,
|
||||
use_cache=True,
|
||||
vocab_size=32000, # 128256,
|
||||
@@ -1035,8 +1018,6 @@ if OLMO3_AVAILABLE:
|
||||
num_hidden_layers=4, # 40
|
||||
num_key_value_heads=2, # 8
|
||||
rms_norm_eps=1e-5,
|
||||
rope_scaling=None,
|
||||
rope_theta=500_000,
|
||||
tie_word_embeddings=False,
|
||||
use_cache=True,
|
||||
vocab_size=32000, # 128256,
|
||||
@@ -1065,8 +1046,6 @@ if GLM4_AVAILABLE:
|
||||
num_hidden_layers=4, # 61
|
||||
num_key_value_heads=2,
|
||||
rms_norm_eps=1e-5,
|
||||
rope_scaling=None,
|
||||
rope_theta=500_000,
|
||||
tie_word_embeddings=False,
|
||||
use_cache=True,
|
||||
vocab_size=32000, # 151552
|
||||
@@ -1102,8 +1081,6 @@ if GLM4V_AVAILABLE:
|
||||
num_hidden_layers=4, # 61
|
||||
num_key_value_heads=2,
|
||||
rms_norm_eps=1e-5,
|
||||
rope_scaling=None,
|
||||
rope_theta=500_000,
|
||||
tie_word_embeddings=False,
|
||||
use_cache=True,
|
||||
vocab_size=32000, # 151552
|
||||
@@ -1119,13 +1096,14 @@ if GLM4V_AVAILABLE:
|
||||
"num_hidden_layers": 4,
|
||||
"num_key_value_heads": 2,
|
||||
"rms_norm_eps": 1e-5,
|
||||
"rope_scaling": {
|
||||
"type": "default",
|
||||
"mrope_section": [8, 12, 12], # (temporal, height, width)
|
||||
},
|
||||
"rope_theta": 500_000,
|
||||
"vocab_size": 32000,
|
||||
"attention_bias": True,
|
||||
**(
|
||||
{"rope_scaling": {"type": "default", "mrope_section": [8, 12, 12]}}
|
||||
if not IS_TRANSFORMERS_V5_OR_LATER
|
||||
else {}
|
||||
),
|
||||
"pad_token_id": None,
|
||||
},
|
||||
vision_config={
|
||||
"depth": 4, # 32
|
||||
@@ -1169,8 +1147,6 @@ if GLM4V_MOE_AVAILABLE:
|
||||
num_hidden_layers=4, # 61
|
||||
num_key_value_heads=2,
|
||||
rms_norm_eps=1e-5,
|
||||
rope_scaling=None,
|
||||
rope_theta=500_000,
|
||||
tie_word_embeddings=False,
|
||||
use_cache=True,
|
||||
vocab_size=32000, # 151552
|
||||
@@ -1186,11 +1162,6 @@ if GLM4V_MOE_AVAILABLE:
|
||||
"num_hidden_layers": 4,
|
||||
"num_key_value_heads": 2,
|
||||
"rms_norm_eps": 1e-5,
|
||||
"rope_scaling": {
|
||||
"type": "default",
|
||||
"mrope_section": [8, 12, 12], # (temporal, height, width)
|
||||
},
|
||||
"rope_theta": 500_000,
|
||||
"vocab_size": 32000,
|
||||
"attention_bias": True,
|
||||
"attention_dropout": 0.0,
|
||||
@@ -1203,6 +1174,11 @@ if GLM4V_MOE_AVAILABLE:
|
||||
"topk_group": 1,
|
||||
"first_k_dense_replace": 1,
|
||||
"norm_topk_prob": True,
|
||||
**(
|
||||
{"rope_scaling": {"type": "default", "mrope_section": [8, 12, 12]}}
|
||||
if not IS_TRANSFORMERS_V5_OR_LATER
|
||||
else {}
|
||||
),
|
||||
},
|
||||
vision_config={
|
||||
"depth": 4, # 32
|
||||
@@ -1238,8 +1214,6 @@ if LLAVA_AVAILABLE:
|
||||
num_hidden_layers=4,
|
||||
num_key_value_heads=2,
|
||||
pretraining_tp=1,
|
||||
rope_scaling=None,
|
||||
rope_theta=500000.0,
|
||||
tie_word_embeddings=False,
|
||||
use_cache=True,
|
||||
max_position_embeddings=4096, # llava-1.5-7b-hf
|
||||
@@ -1298,8 +1272,6 @@ if SMOLLM3_AVAILABLE:
|
||||
num_key_value_heads=2, # 8
|
||||
pretraining_tp=1,
|
||||
rms_norm_eps=1e-5,
|
||||
rope_scaling=None,
|
||||
rope_theta=500000.0,
|
||||
tie_word_embeddings=False,
|
||||
use_cache=True,
|
||||
vocab_size=32000, # 128256,
|
||||
@@ -1390,8 +1362,6 @@ if QWEN3NEXT_AVAILABLE:
|
||||
rms_norm_eps=1e-6,
|
||||
use_cache=True,
|
||||
tie_word_embeddings=False,
|
||||
rope_theta=10000.0,
|
||||
rope_scaling=None,
|
||||
attention_bias=False,
|
||||
use_sliding_window=False,
|
||||
sliding_window=4096,
|
||||
@@ -1430,7 +1400,6 @@ if HUNYUAN_V1_AVAILABLE:
|
||||
initializer_range=0.02,
|
||||
norm_eps=1e-6,
|
||||
num_key_value_heads=2,
|
||||
rope_theta=10000.0,
|
||||
partial_rotary_factor=1.0,
|
||||
vocab_size=32000,
|
||||
use_cache=True,
|
||||
@@ -1456,7 +1425,6 @@ if HUNYUAN_V1_AVAILABLE:
|
||||
initializer_range=0.02,
|
||||
norm_eps=1e-6,
|
||||
num_key_value_heads=2,
|
||||
rope_theta=10000.0,
|
||||
partial_rotary_factor=1.0,
|
||||
vocab_size=32000,
|
||||
num_experts=8,
|
||||
@@ -1484,11 +1452,11 @@ if EXAONE4_AVAILABLE:
|
||||
num_hidden_layers=4,
|
||||
num_key_value_heads=2,
|
||||
rms_norm_eps=1e-5,
|
||||
rope_theta=1000000.0,
|
||||
tie_word_embeddings=True,
|
||||
use_cache=True,
|
||||
vocab_size=32000,
|
||||
attn_implementation="sdpa",
|
||||
pad_token_id=None,
|
||||
),
|
||||
)
|
||||
|
||||
@@ -1559,7 +1527,6 @@ def run_mini_model(
|
||||
optimizer = torch.optim.AdamW(model.parameters(), lr=lr)
|
||||
|
||||
loss_list = []
|
||||
|
||||
for i in range(num_steps):
|
||||
batch = next(loader_iter).to(model.device)
|
||||
optimizer.zero_grad()
|
||||
@@ -1590,12 +1557,12 @@ def run_mini_model(
|
||||
"model_name, num_steps, lr, dtype, loss_atol, loss_rtol, logprobs_atol, logprobs_rtol, param_atol, param_rtol",
|
||||
[
|
||||
pytest.param(
|
||||
"mini_llama4",
|
||||
"mini_llama4", # llama4 requires slightly larger tolerances to pass this test after bug fix to llama4 in transformers v5.0.0
|
||||
32,
|
||||
1e-4,
|
||||
torch.float32,
|
||||
1e-8,
|
||||
1e-5,
|
||||
1e-3,
|
||||
5e-3,
|
||||
1e-3,
|
||||
5e-3,
|
||||
@@ -1876,10 +1843,7 @@ def run_mini_model(
|
||||
1e-5,
|
||||
5e-3,
|
||||
1e-5,
|
||||
marks=pytest.mark.skipif(
|
||||
version.parse(transformers.__version__) < version.parse("4.49.0"),
|
||||
reason="Mistral not available in transformers<=4.49.0",
|
||||
),
|
||||
marks=[],
|
||||
),
|
||||
# TODO: mixtral is flaky so disable the test for now
|
||||
# ("mini_mixtral", 32, 1e-4, torch.float32, 5e-4, 1e-4, 5e-3, 1e-5, 1e-2, 1e-5),
|
||||
|
||||
@@ -5,11 +5,12 @@ os.environ["CUBLAS_WORKSPACE_CONFIG"] = ":4096:8" # Ensure deterministic behavi
|
||||
|
||||
import pytest
|
||||
import torch
|
||||
import transformers
|
||||
|
||||
from datasets import load_dataset
|
||||
from packaging import version
|
||||
from torch.utils.data import DataLoader
|
||||
from transformers import PreTrainedTokenizerFast
|
||||
from transformers.models.gemma.tokenization_gemma_fast import GemmaTokenizerFast
|
||||
from transformers.models.siglip.configuration_siglip import SiglipVisionConfig
|
||||
|
||||
from liger_kernel.transformers import apply_liger_kernel_to_gemma3
|
||||
@@ -23,6 +24,7 @@ from liger_kernel.transformers import apply_liger_kernel_to_qwen2_vl
|
||||
from liger_kernel.transformers import apply_liger_kernel_to_qwen3_vl
|
||||
from liger_kernel.transformers import apply_liger_kernel_to_qwen3_vl_moe
|
||||
from liger_kernel.transformers import apply_liger_kernel_to_smolvlm
|
||||
from liger_kernel.utils import infer_device
|
||||
from test.utils import FAKE_CONFIGS_PATH
|
||||
from test.utils import UNTOKENIZED_DATASET_PATH
|
||||
from test.utils import MiniModelConfig
|
||||
@@ -49,12 +51,23 @@ from test.utils import revert_liger_kernel_to_smolvlm2
|
||||
from test.utils import set_seed
|
||||
from test.utils import train_bpe_tokenizer
|
||||
|
||||
IS_TRANSFORMERS_V5_OR_LATER = version.parse(transformers.__version__) >= version.parse("5.0.0")
|
||||
|
||||
if IS_TRANSFORMERS_V5_OR_LATER:
|
||||
from transformers.models.gemma.tokenization_gemma import GemmaTokenizer
|
||||
else:
|
||||
from transformers.models.gemma.tokenization_gemma_fast import GemmaTokenizerFast as GemmaTokenizer
|
||||
|
||||
try:
|
||||
# Qwen2-VL is only available in transformers>=4.52.4
|
||||
import transformers
|
||||
|
||||
from packaging import version
|
||||
from transformers.models.qwen2.tokenization_qwen2_fast import Qwen2TokenizerFast
|
||||
|
||||
if IS_TRANSFORMERS_V5_OR_LATER:
|
||||
from transformers.models.qwen2.tokenization_qwen2 import Qwen2Tokenizer
|
||||
else:
|
||||
from transformers.models.qwen2.tokenization_qwen2_fast import Qwen2TokenizerFast as Qwen2Tokenizer
|
||||
from transformers.models.qwen2_vl.configuration_qwen2_vl import Qwen2VLConfig
|
||||
from transformers.models.qwen2_vl.image_processing_qwen2_vl import Qwen2VLImageProcessor
|
||||
from transformers.models.qwen2_vl.modeling_qwen2_vl import Qwen2VLForConditionalGeneration
|
||||
@@ -70,7 +83,11 @@ try:
|
||||
import transformers
|
||||
|
||||
from packaging import version
|
||||
from transformers.models.qwen2.tokenization_qwen2_fast import Qwen2TokenizerFast
|
||||
|
||||
if IS_TRANSFORMERS_V5_OR_LATER:
|
||||
from transformers.models.qwen2.tokenization_qwen2 import Qwen2Tokenizer
|
||||
else:
|
||||
from transformers.models.qwen2.tokenization_qwen2_fast import Qwen2TokenizerFast as Qwen2Tokenizer
|
||||
from transformers.models.qwen2_5_vl.configuration_qwen2_5_vl import Qwen2_5_VLConfig
|
||||
from transformers.models.qwen2_5_vl.modeling_qwen2_5_vl import Qwen2_5_VLForConditionalGeneration
|
||||
from transformers.models.qwen2_5_vl.processing_qwen2_5_vl import Qwen2_5_VLProcessor
|
||||
@@ -83,7 +100,10 @@ except ImportError:
|
||||
|
||||
|
||||
try:
|
||||
from transformers.models.qwen2.tokenization_qwen2_fast import Qwen2TokenizerFast
|
||||
if IS_TRANSFORMERS_V5_OR_LATER:
|
||||
from transformers.models.qwen2.tokenization_qwen2 import Qwen2Tokenizer
|
||||
else:
|
||||
from transformers.models.qwen2.tokenization_qwen2_fast import Qwen2TokenizerFast as Qwen2Tokenizer
|
||||
from transformers.models.qwen2_vl.image_processing_qwen2_vl import Qwen2VLImageProcessor
|
||||
from transformers.models.qwen3_vl.configuration_qwen3_vl import Qwen3VLConfig
|
||||
from transformers.models.qwen3_vl.configuration_qwen3_vl import Qwen3VLTextConfig
|
||||
@@ -108,7 +128,10 @@ except ImportError:
|
||||
QWEN3_VL_MOE_AVAILABLE = False
|
||||
|
||||
try:
|
||||
from transformers.models.qwen2.tokenization_qwen2_fast import Qwen2TokenizerFast
|
||||
if IS_TRANSFORMERS_V5_OR_LATER:
|
||||
from transformers.models.qwen2.tokenization_qwen2 import Qwen2Tokenizer
|
||||
else:
|
||||
from transformers.models.qwen2.tokenization_qwen2_fast import Qwen2TokenizerFast as Qwen2Tokenizer
|
||||
from transformers.models.qwen2_vl.image_processing_qwen2_vl import Qwen2VLImageProcessor
|
||||
from transformers.models.qwen3_vl.configuration_qwen3_vl import Qwen3VLConfig
|
||||
from transformers.models.qwen3_vl.configuration_qwen3_vl import Qwen3VLTextConfig
|
||||
@@ -183,7 +206,7 @@ try:
|
||||
from transformers.models.paligemma.processing_paligemma import PaliGemmaProcessor
|
||||
from transformers.models.siglip.image_processing_siglip import SiglipImageProcessor
|
||||
|
||||
PALIGEMMA_AVAILABLE = version.parse(transformers.__version__) >= version.parse("4.46.0")
|
||||
PALIGEMMA_AVAILABLE = True
|
||||
except ImportError:
|
||||
PALIGEMMA_AVAILABLE = False
|
||||
|
||||
@@ -214,7 +237,7 @@ except ImportError:
|
||||
|
||||
try:
|
||||
# SmolVLM2 is only available in transformers>=4.50.0
|
||||
from transformers.models.gpt2.tokenization_gpt2_fast import GPT2TokenizerFast
|
||||
from transformers.models.gpt2.tokenization_gpt2 import GPT2Tokenizer
|
||||
from transformers.models.smolvlm.configuration_smolvlm import SmolVLMConfig
|
||||
from transformers.models.smolvlm.image_processing_smolvlm import SmolVLMImageProcessor
|
||||
from transformers.models.smolvlm.modeling_smolvlm import SmolVLMForConditionalGeneration
|
||||
@@ -232,7 +255,6 @@ try:
|
||||
except ImportError:
|
||||
NUM2WORDS_AVAILABLE = False
|
||||
|
||||
from liger_kernel.utils import infer_device
|
||||
|
||||
device = infer_device()
|
||||
|
||||
@@ -291,7 +313,6 @@ if LLAMA4_AVAILABLE:
|
||||
num_hidden_layers=4, # 40
|
||||
num_key_value_heads=2, # 8
|
||||
rms_norm_eps=1e-5,
|
||||
rope_theta=500_000,
|
||||
tie_word_embeddings=False,
|
||||
use_cache=True,
|
||||
vocab_size=32000, # 128256,
|
||||
@@ -345,8 +366,9 @@ if MLLAMA_AVAILABLE:
|
||||
low_freq_factor=1.0,
|
||||
original_max_position_embeddings=8192,
|
||||
rope_type="llama3",
|
||||
),
|
||||
rope_theta=500_000,
|
||||
)
|
||||
if not IS_TRANSFORMERS_V5_OR_LATER
|
||||
else None,
|
||||
tie_word_embeddings=False,
|
||||
use_cache=True,
|
||||
vocab_size=32000, # 128256,
|
||||
@@ -396,7 +418,6 @@ if PALIGEMMA_AVAILABLE:
|
||||
bos_token_id=1, # 128000
|
||||
eos_token_id=2, # 128001
|
||||
tie_word_embeddings=True,
|
||||
rope_theta=10000.0,
|
||||
attention_bias=False,
|
||||
attention_dropout=0.0,
|
||||
),
|
||||
@@ -446,7 +467,6 @@ if PALIGEMMA_AVAILABLE:
|
||||
bos_token_id=1, # 128000
|
||||
eos_token_id=2, # 128001
|
||||
tie_word_embeddings=True,
|
||||
rope_theta=10000.0,
|
||||
attention_bias=False,
|
||||
attention_dropout=0.0,
|
||||
),
|
||||
@@ -492,7 +512,6 @@ if GEMMA3_AVAILABLE:
|
||||
rms_norm_eps=1e-06,
|
||||
use_cache=True,
|
||||
tie_word_embeddings=True,
|
||||
rope_theta=10000.0,
|
||||
attention_bias=False,
|
||||
attention_dropout=0.0,
|
||||
),
|
||||
@@ -528,10 +547,10 @@ if QWEN2_VL_AVAILABLE:
|
||||
num_hidden_layers=4, # 80
|
||||
num_key_value_heads=2, # 8
|
||||
rms_norm_eps=1e-6, # 1e-5
|
||||
rope_theta=1000000.0,
|
||||
rope_scaling=dict(
|
||||
type="mrope",
|
||||
mrope_section=[16, 24, 24], # (temporal, height, width)
|
||||
**(
|
||||
dict(rope_parameters=dict(mrope_section=[16, 24, 24])) # (temporal, height, width)
|
||||
if IS_TRANSFORMERS_V5_OR_LATER
|
||||
else dict(rope_scaling=dict(type="mrope", mrope_section=[16, 24, 24]))
|
||||
),
|
||||
sliding_window=4096,
|
||||
tie_word_embeddings=True,
|
||||
@@ -570,8 +589,6 @@ if LLAVA_AVAILABLE:
|
||||
num_hidden_layers=4,
|
||||
num_key_value_heads=2,
|
||||
pretraining_tp=1,
|
||||
rope_scaling=None,
|
||||
rope_theta=500000.0,
|
||||
tie_word_embeddings=False,
|
||||
use_cache=True,
|
||||
max_position_embeddings=4096, # llava-1.5-7b-hf
|
||||
@@ -662,7 +679,6 @@ if SMOLVLM2_AVAILABLE:
|
||||
num_hidden_layers=4, # 30 -> reduced to 4 for testing
|
||||
num_key_value_heads=3, # 3 for 256M model
|
||||
rms_norm_eps=1e-5,
|
||||
rope_theta=100000,
|
||||
tie_word_embeddings=False,
|
||||
vocab_size=49280,
|
||||
),
|
||||
@@ -705,10 +721,10 @@ if QWEN2_5_VL_AVAILABLE:
|
||||
num_hidden_layers=4, # 80
|
||||
num_key_value_heads=2, # 8
|
||||
rms_norm_eps=1e-6, # 1e-5
|
||||
rope_theta=1000000.0,
|
||||
rope_scaling=dict(
|
||||
type="mrope",
|
||||
mrope_section=[16, 24, 24], # (temporal, height, width)
|
||||
**(
|
||||
dict(rope_parameters=dict(mrope_section=[16, 24, 24])) # (temporal, height, width)
|
||||
if IS_TRANSFORMERS_V5_OR_LATER
|
||||
else dict(rope_scaling=dict(type="mrope", mrope_section=[16, 24, 24]))
|
||||
),
|
||||
sliding_window=4096,
|
||||
tie_word_embeddings=True,
|
||||
@@ -767,11 +783,6 @@ if QWEN3_VL_AVAILABLE:
|
||||
rms_norm_eps=1e-6,
|
||||
use_cache=False,
|
||||
tie_word_embeddings=True,
|
||||
rope_theta=1000000.0,
|
||||
rope_scaling=dict(
|
||||
type="mrope",
|
||||
mrope_section=[16, 24, 24],
|
||||
),
|
||||
attention_dropout=0.0,
|
||||
attention_bias=False,
|
||||
).to_dict(),
|
||||
@@ -819,11 +830,6 @@ if QWEN3_VL_MOE_AVAILABLE:
|
||||
rms_norm_eps=1e-6,
|
||||
use_cache=False,
|
||||
tie_word_embeddings=True,
|
||||
rope_theta=1000000.0,
|
||||
rope_scaling=dict(
|
||||
type="mrope",
|
||||
mrope_section=[16, 24, 24],
|
||||
),
|
||||
attention_dropout=0.0,
|
||||
attention_bias=False,
|
||||
decoder_sparse_step=1,
|
||||
@@ -879,11 +885,6 @@ if QWEN3_VL_AVAILABLE:
|
||||
rms_norm_eps=1e-6,
|
||||
use_cache=False,
|
||||
tie_word_embeddings=True,
|
||||
rope_theta=1000000.0,
|
||||
rope_scaling=dict(
|
||||
type="mrope",
|
||||
mrope_section=[16, 24, 24],
|
||||
),
|
||||
attention_dropout=0.0,
|
||||
attention_bias=False,
|
||||
).to_dict(),
|
||||
@@ -931,11 +932,6 @@ if QWEN3_VL_MOE_AVAILABLE:
|
||||
rms_norm_eps=1e-6,
|
||||
use_cache=False,
|
||||
tie_word_embeddings=True,
|
||||
rope_theta=1000000.0,
|
||||
rope_scaling=dict(
|
||||
type="mrope",
|
||||
mrope_section=[16, 24, 24],
|
||||
),
|
||||
attention_dropout=0.0,
|
||||
attention_bias=False,
|
||||
decoder_sparse_step=1,
|
||||
@@ -962,7 +958,7 @@ def create_processor(model_name: str):
|
||||
)
|
||||
]
|
||||
)
|
||||
qwen_tokenizer = Qwen2TokenizerFast(tokenizer_object=tokenizer_base, **tokenizer_config)
|
||||
qwen_tokenizer = Qwen2Tokenizer(tokenizer_object=tokenizer_base, **tokenizer_config)
|
||||
image_processor = Qwen2VLImageProcessor()
|
||||
video_processor = Qwen2VLVideoProcessor()
|
||||
return Qwen2VLProcessor(
|
||||
@@ -984,7 +980,7 @@ def create_processor(model_name: str):
|
||||
)
|
||||
]
|
||||
)
|
||||
qwen_tokenizer = Qwen2TokenizerFast(tokenizer_object=tokenizer_base, **tokenizer_config)
|
||||
qwen_tokenizer = Qwen2Tokenizer(tokenizer_object=tokenizer_base, **tokenizer_config)
|
||||
image_processor = Qwen2VLImageProcessor()
|
||||
video_processor = Qwen2VLVideoProcessor()
|
||||
return Qwen2_5_VLProcessor(
|
||||
@@ -1006,7 +1002,7 @@ def create_processor(model_name: str):
|
||||
)
|
||||
]
|
||||
)
|
||||
qwen_tokenizer = Qwen2TokenizerFast(tokenizer_object=tokenizer_base, **tokenizer_config)
|
||||
qwen_tokenizer = Qwen2Tokenizer(tokenizer_object=tokenizer_base, **tokenizer_config)
|
||||
image_processor = Qwen2VLImageProcessor(patch_size=16, temporal_patch_size=2, merge_size=2)
|
||||
video_processor = Qwen3VLVideoProcessor()
|
||||
return Qwen3VLProcessor(
|
||||
@@ -1063,7 +1059,7 @@ def create_processor(model_name: str):
|
||||
)
|
||||
]
|
||||
)
|
||||
qwen_tokenizer = Qwen2TokenizerFast(tokenizer_object=tokenizer_base, **tokenizer_config)
|
||||
qwen_tokenizer = Qwen2Tokenizer(tokenizer_object=tokenizer_base, **tokenizer_config)
|
||||
image_processor = GotOcr2ImageProcessorFast(
|
||||
crop_to_patches=False, min_patches=1, max_patches=12, size={"height": 448, "width": 448}
|
||||
)
|
||||
@@ -1087,7 +1083,7 @@ def create_processor(model_name: str):
|
||||
)
|
||||
]
|
||||
)
|
||||
gpt2_tokenizer = GPT2TokenizerFast(tokenizer_object=tokenizer_base, **tokenizer_config)
|
||||
gpt2_tokenizer = GPT2Tokenizer(tokenizer_object=tokenizer_base, **tokenizer_config)
|
||||
image_processor = SmolVLMImageProcessor(size={"longest_edge": 512})
|
||||
video_processor = SmolVLMVideoProcessor()
|
||||
|
||||
@@ -1157,7 +1153,7 @@ def create_processor(model_name: str):
|
||||
)
|
||||
]
|
||||
)
|
||||
fast_tokenizer = GemmaTokenizerFast(tokenizer_object=tokenizer_base, **tokenizer_config)
|
||||
fast_tokenizer = GemmaTokenizer(tokenizer_object=tokenizer_base, **tokenizer_config)
|
||||
image_processor = SiglipImageProcessor(size={"height": 224, "width": 224}, image_seq_length=256)
|
||||
return PaliGemmaProcessor(image_processor=image_processor, tokenizer=fast_tokenizer)
|
||||
|
||||
@@ -1177,7 +1173,7 @@ def create_processor(model_name: str):
|
||||
)
|
||||
]
|
||||
)
|
||||
fast_tokenizer = GemmaTokenizerFast(tokenizer_object=tokenizer_base, **tokenizer_config)
|
||||
fast_tokenizer = GemmaTokenizer(tokenizer_object=tokenizer_base, **tokenizer_config)
|
||||
image_processor = Gemma3ImageProcessor()
|
||||
return Gemma3Processor(image_processor=image_processor, tokenizer=fast_tokenizer)
|
||||
|
||||
|
||||
@@ -4,8 +4,10 @@ os.environ["CUBLAS_WORKSPACE_CONFIG"] = ":4096:8" # Ensure deterministic behavi
|
||||
|
||||
import pytest
|
||||
import torch
|
||||
import transformers
|
||||
|
||||
from datasets import load_from_disk
|
||||
from packaging import version
|
||||
from torch.utils.data import DataLoader
|
||||
from transformers.models.gemma import GemmaConfig
|
||||
from transformers.models.gemma import GemmaForCausalLM
|
||||
@@ -52,6 +54,7 @@ from liger_kernel.transformers import apply_liger_kernel_to_qwen3_next
|
||||
from liger_kernel.transformers import apply_liger_kernel_to_qwen3_vl
|
||||
from liger_kernel.transformers import apply_liger_kernel_to_qwen3_vl_moe
|
||||
from liger_kernel.transformers import apply_liger_kernel_to_smollm3
|
||||
from liger_kernel.utils import infer_device
|
||||
from test.utils import DEFAULT_DATASET_PATH
|
||||
from test.utils import MiniModelConfig
|
||||
from test.utils import assert_verbose_allclose
|
||||
@@ -91,6 +94,8 @@ from test.utils import revert_liger_kernel_to_smollm3
|
||||
from test.utils import set_seed
|
||||
from test.utils import simple_collate_fn
|
||||
|
||||
IS_TRANSFORMERS_V5_OR_LATER = version.parse(transformers.__version__) >= version.parse("5.0.0")
|
||||
|
||||
try:
|
||||
from transformers.models.llama4.configuration_llama4 import Llama4TextConfig
|
||||
from transformers.models.llama4.modeling_llama4 import Llama4ForCausalLM
|
||||
@@ -309,8 +314,6 @@ except ImportError:
|
||||
EXAONE4_AVAILABLE = False
|
||||
|
||||
|
||||
from liger_kernel.utils import infer_device
|
||||
|
||||
device = infer_device()
|
||||
|
||||
MINI_MODEL_SETUPS = {
|
||||
@@ -335,8 +338,6 @@ MINI_MODEL_SETUPS = {
|
||||
num_key_value_heads=2, # 8
|
||||
pretraining_tp=1,
|
||||
rms_norm_eps=1e-5,
|
||||
rope_scaling=None,
|
||||
rope_theta=500000.0,
|
||||
tie_word_embeddings=False,
|
||||
use_cache=True,
|
||||
vocab_size=32000, # 128256,
|
||||
@@ -364,7 +365,6 @@ MINI_MODEL_SETUPS = {
|
||||
num_hidden_layers=4,
|
||||
num_key_value_heads=2,
|
||||
rms_norm_eps=1e-6,
|
||||
rope_theta=1000000.0,
|
||||
sliding_window=131072,
|
||||
tie_word_embeddings=True,
|
||||
use_cache=True,
|
||||
@@ -393,7 +393,6 @@ MINI_MODEL_SETUPS = {
|
||||
num_hidden_layers=4, # 32
|
||||
num_key_value_heads=None, # defaults to num_attention_heads
|
||||
rms_norm_eps=1e-5,
|
||||
rope_theta=10000.0,
|
||||
sliding_window=None,
|
||||
tie_word_embeddings=False,
|
||||
use_cache=True,
|
||||
@@ -418,7 +417,6 @@ MINI_MODEL_SETUPS = {
|
||||
num_hidden_layers=4,
|
||||
num_key_value_heads=2,
|
||||
rms_norm_eps=1e-5,
|
||||
rope_theta=10000.0,
|
||||
sliding_window=4096,
|
||||
tie_word_embeddings=False,
|
||||
use_cache=True,
|
||||
@@ -443,7 +441,6 @@ MINI_MODEL_SETUPS = {
|
||||
num_hidden_layers=4, # 32
|
||||
num_key_value_heads=2, # 8
|
||||
rms_norm_eps=1e-5,
|
||||
rope_theta=10000.0,
|
||||
sliding_window=4096,
|
||||
tie_word_embeddings=False,
|
||||
use_cache=True,
|
||||
@@ -478,7 +475,6 @@ MINI_MODEL_SETUPS = {
|
||||
bos_token_id=1, # 128000
|
||||
eos_token_id=2, # 128001
|
||||
tie_word_embeddings=True,
|
||||
rope_theta=10000.0,
|
||||
attention_bias=False,
|
||||
attention_dropout=0.0,
|
||||
),
|
||||
@@ -506,7 +502,6 @@ MINI_MODEL_SETUPS = {
|
||||
bos_token_id=1, # 128000
|
||||
eos_token_id=2, # 128001
|
||||
tie_word_embeddings=True,
|
||||
rope_theta=10000.0,
|
||||
attention_bias=False,
|
||||
attention_dropout=0.0,
|
||||
),
|
||||
@@ -534,7 +529,6 @@ MINI_MODEL_SETUPS = {
|
||||
bos_token_id=1, # 128000
|
||||
eos_token_id=2, # 128001
|
||||
tie_word_embeddings=True,
|
||||
rope_theta=10000.0,
|
||||
attention_bias=False,
|
||||
attention_dropout=0.0,
|
||||
attn_implementation="eager",
|
||||
@@ -562,8 +556,6 @@ if LLAMA4_AVAILABLE:
|
||||
num_hidden_layers=4, # 61
|
||||
num_key_value_heads=2,
|
||||
rms_norm_eps=1e-5,
|
||||
rope_scaling=None,
|
||||
rope_theta=10000.0,
|
||||
tie_word_embeddings=False,
|
||||
use_cache=True,
|
||||
vocab_size=32000, # 151552
|
||||
@@ -590,7 +582,6 @@ if QWEN3_AVAILABLE:
|
||||
num_hidden_layers=4,
|
||||
num_key_value_heads=2,
|
||||
rms_norm_eps=1e-6,
|
||||
rope_theta=1000000.0,
|
||||
sliding_window=131072,
|
||||
tie_word_embeddings=True,
|
||||
use_cache=True,
|
||||
@@ -616,8 +607,6 @@ if QWEN3_AVAILABLE:
|
||||
rms_norm_eps=1e-6,
|
||||
use_cache=True,
|
||||
tie_word_embeddings=False,
|
||||
rope_theta=10000.0,
|
||||
rope_scaling=None,
|
||||
attention_bias=False,
|
||||
use_sliding_window=False,
|
||||
sliding_window=4096,
|
||||
@@ -656,7 +645,6 @@ if GEMMA3_AVAILABLE:
|
||||
bos_token_id=2,
|
||||
eos_token_id=1,
|
||||
tie_word_embeddings=True,
|
||||
rope_theta=10000.0, # 1000000
|
||||
attention_bias=False,
|
||||
attention_dropout=0.0,
|
||||
attn_implementation="eager",
|
||||
@@ -683,18 +671,20 @@ if MLLAMA_AVAILABLE:
|
||||
num_hidden_layers=4, # 40
|
||||
num_key_value_heads=2, # 8
|
||||
rms_norm_eps=1e-5,
|
||||
tie_word_embeddings=False,
|
||||
use_cache=True,
|
||||
vocab_size=32000, # 128256,
|
||||
attn_implementation="sdpa", # default value, pytorch native attention
|
||||
rope_scaling=dict(
|
||||
factor=8.0,
|
||||
high_freq_factor=4.0,
|
||||
low_freq_factor=1.0,
|
||||
original_max_position_embeddings=8192,
|
||||
rope_type="llama3",
|
||||
),
|
||||
rope_theta=500_000,
|
||||
tie_word_embeddings=False,
|
||||
use_cache=True,
|
||||
vocab_size=32000, # 128256,
|
||||
attn_implementation="sdpa", # default value, pytorch native attention
|
||||
rope_theta=500_000,
|
||||
)
|
||||
if not IS_TRANSFORMERS_V5_OR_LATER
|
||||
else None,
|
||||
),
|
||||
)
|
||||
|
||||
@@ -724,10 +714,10 @@ if QWEN2_VL_AVAILABLE:
|
||||
num_hidden_layers=4, # 80
|
||||
num_key_value_heads=2, # 8
|
||||
rms_norm_eps=1e-6, # 1e-5
|
||||
rope_theta=1000000.0,
|
||||
rope_scaling=dict(
|
||||
type="mrope",
|
||||
mrope_section=[16, 24, 24], # (temporal, height, width)
|
||||
**(
|
||||
dict(rope_parameters=dict(mrope_section=[16, 24, 24])) # (temporal, height, width)
|
||||
if IS_TRANSFORMERS_V5_OR_LATER
|
||||
else dict(rope_scaling=dict(type="mrope", mrope_section=[16, 24, 24]))
|
||||
),
|
||||
sliding_window=4096,
|
||||
tie_word_embeddings=False,
|
||||
@@ -776,10 +766,10 @@ if QWEN2_5_VL_AVAILABLE:
|
||||
num_hidden_layers=4, # 80
|
||||
num_key_value_heads=2, # 8
|
||||
rms_norm_eps=1e-6, # 1e-5
|
||||
rope_theta=1000000.0,
|
||||
rope_scaling=dict(
|
||||
type="mrope",
|
||||
mrope_section=[16, 24, 24], # (temporal, height, width)
|
||||
**(
|
||||
dict(rope_parameters=dict(mrope_section=[16, 24, 24])) # (temporal, height, width)
|
||||
if IS_TRANSFORMERS_V5_OR_LATER
|
||||
else dict(rope_scaling=dict(type="mrope", mrope_section=[16, 24, 24]))
|
||||
),
|
||||
sliding_window=4096,
|
||||
tie_word_embeddings=False,
|
||||
@@ -833,15 +823,16 @@ if QWEN3_VL_AVAILABLE:
|
||||
num_key_value_heads=2,
|
||||
pad_token_id=2,
|
||||
rms_norm_eps=1e-6,
|
||||
rope_theta=1000000.0,
|
||||
rope_scaling=dict(
|
||||
type="mrope",
|
||||
mrope_section=[16, 24, 24],
|
||||
),
|
||||
sliding_window=131072,
|
||||
tie_word_embeddings=False,
|
||||
use_cache=True,
|
||||
vocab_size=32000,
|
||||
rope_scaling=dict(
|
||||
type="mrope",
|
||||
mrope_section=[16, 24, 24], # (temporal, height, width)
|
||||
)
|
||||
if not IS_TRANSFORMERS_V5_OR_LATER
|
||||
else None,
|
||||
),
|
||||
vision_config=dict(
|
||||
depth=4,
|
||||
@@ -888,11 +879,6 @@ if QWEN3_VL_MOE_AVAILABLE:
|
||||
num_key_value_heads=2,
|
||||
pad_token_id=2,
|
||||
rms_norm_eps=1e-6,
|
||||
rope_theta=1000000.0,
|
||||
rope_scaling=dict(
|
||||
type="mrope",
|
||||
mrope_section=[16, 24, 24],
|
||||
),
|
||||
sliding_window=131072,
|
||||
tie_word_embeddings=False,
|
||||
use_cache=True,
|
||||
@@ -942,8 +928,6 @@ if GRANITE_AVAILABLE:
|
||||
num_key_value_heads=2, # 8
|
||||
pretraining_tp=1,
|
||||
rms_norm_eps=1e-5,
|
||||
rope_scaling=None,
|
||||
rope_theta=500000.0,
|
||||
tie_word_embeddings=False,
|
||||
use_cache=True,
|
||||
vocab_size=32000, # 128256,
|
||||
@@ -976,8 +960,6 @@ if LLAVA_AVAILABLE:
|
||||
num_hidden_layers=4,
|
||||
num_key_value_heads=2,
|
||||
pretraining_tp=1,
|
||||
rope_scaling=None,
|
||||
rope_theta=500000.0,
|
||||
tie_word_embeddings=False,
|
||||
use_cache=True,
|
||||
max_position_embeddings=4096, # llava-1.5-7b-hf
|
||||
@@ -1035,8 +1017,6 @@ if OLMO2_AVAILABLE:
|
||||
num_hidden_layers=4, # 40
|
||||
num_key_value_heads=2, # 8
|
||||
rms_norm_eps=1e-5,
|
||||
rope_scaling=None,
|
||||
rope_theta=500_000,
|
||||
tie_word_embeddings=False,
|
||||
use_cache=True,
|
||||
vocab_size=32000, # 128256,
|
||||
@@ -1064,8 +1044,6 @@ if OLMO3_AVAILABLE:
|
||||
num_hidden_layers=4, # 40
|
||||
num_key_value_heads=2, # 8
|
||||
rms_norm_eps=1e-5,
|
||||
rope_scaling=None,
|
||||
rope_theta=500_000,
|
||||
tie_word_embeddings=False,
|
||||
use_cache=True,
|
||||
vocab_size=32000, # 128256,
|
||||
@@ -1094,8 +1072,6 @@ if GLM4_AVAILABLE:
|
||||
num_hidden_layers=4, # 61
|
||||
num_key_value_heads=2,
|
||||
rms_norm_eps=1e-5,
|
||||
rope_scaling=None,
|
||||
rope_theta=500_000,
|
||||
tie_word_embeddings=False,
|
||||
use_cache=True,
|
||||
vocab_size=32000, # 151552
|
||||
@@ -1131,8 +1107,6 @@ if GLM4V_AVAILABLE:
|
||||
num_hidden_layers=4, # 61
|
||||
num_key_value_heads=2,
|
||||
rms_norm_eps=1e-5,
|
||||
rope_scaling=None,
|
||||
rope_theta=500_000,
|
||||
tie_word_embeddings=False,
|
||||
use_cache=True,
|
||||
vocab_size=32000, # 151552
|
||||
@@ -1148,13 +1122,14 @@ if GLM4V_AVAILABLE:
|
||||
"num_hidden_layers": 4,
|
||||
"num_key_value_heads": 2,
|
||||
"rms_norm_eps": 1e-5,
|
||||
"rope_scaling": {
|
||||
"type": "default",
|
||||
"mrope_section": [8, 12, 12], # (temporal, height, width)
|
||||
},
|
||||
"rope_theta": 500_000,
|
||||
"vocab_size": 32000,
|
||||
"attention_bias": True,
|
||||
**(
|
||||
{"rope_scaling": {"type": "default", "mrope_section": [8, 12, 12]}}
|
||||
if not IS_TRANSFORMERS_V5_OR_LATER
|
||||
else {}
|
||||
),
|
||||
"pad_token_id": None,
|
||||
},
|
||||
vision_config={
|
||||
"depth": 4, # 32
|
||||
@@ -1197,8 +1172,6 @@ if GLM4V_MOE_AVAILABLE:
|
||||
num_hidden_layers=4, # 61
|
||||
num_key_value_heads=2,
|
||||
rms_norm_eps=1e-5,
|
||||
rope_scaling=None,
|
||||
rope_theta=500_000,
|
||||
tie_word_embeddings=False,
|
||||
use_cache=True,
|
||||
vocab_size=32000, # 151552
|
||||
@@ -1214,11 +1187,6 @@ if GLM4V_MOE_AVAILABLE:
|
||||
"num_hidden_layers": 4,
|
||||
"num_key_value_heads": 2,
|
||||
"rms_norm_eps": 1e-5,
|
||||
"rope_scaling": {
|
||||
"type": "default",
|
||||
"mrope_section": [8, 12, 12], # (temporal, height, width)
|
||||
},
|
||||
"rope_theta": 500_000,
|
||||
"vocab_size": 32000,
|
||||
"attention_bias": True,
|
||||
"attention_dropout": 0.0,
|
||||
@@ -1231,6 +1199,11 @@ if GLM4V_MOE_AVAILABLE:
|
||||
"topk_group": 1,
|
||||
"first_k_dense_replace": 1,
|
||||
"norm_topk_prob": True,
|
||||
**(
|
||||
{"rope_scaling": {"type": "default", "mrope_section": [8, 12, 12]}}
|
||||
if not IS_TRANSFORMERS_V5_OR_LATER
|
||||
else {}
|
||||
),
|
||||
},
|
||||
vision_config={
|
||||
"depth": 4, # 32
|
||||
@@ -1268,8 +1241,6 @@ if SMOLLM3_AVAILABLE:
|
||||
num_key_value_heads=2, # 8
|
||||
pretraining_tp=1,
|
||||
rms_norm_eps=1e-5,
|
||||
rope_scaling=None,
|
||||
rope_theta=500000.0,
|
||||
tie_word_embeddings=False,
|
||||
use_cache=True,
|
||||
vocab_size=32000, # 128256,
|
||||
@@ -1360,8 +1331,6 @@ if QWEN3NEXT_AVAILABLE:
|
||||
rms_norm_eps=1e-6,
|
||||
use_cache=True,
|
||||
tie_word_embeddings=False,
|
||||
rope_theta=10000.0,
|
||||
rope_scaling=None,
|
||||
attention_bias=False,
|
||||
use_sliding_window=False,
|
||||
sliding_window=4096,
|
||||
@@ -1402,7 +1371,6 @@ if HUNYUAN_V1_AVAILABLE:
|
||||
initializer_range=0.02,
|
||||
norm_eps=1e-6,
|
||||
num_key_value_heads=2,
|
||||
rope_theta=10000.0,
|
||||
partial_rotary_factor=1.0,
|
||||
vocab_size=32000,
|
||||
use_cache=True,
|
||||
@@ -1428,7 +1396,6 @@ if HUNYUAN_V1_AVAILABLE:
|
||||
initializer_range=0.02,
|
||||
norm_eps=1e-6,
|
||||
num_key_value_heads=2,
|
||||
rope_theta=10000.0,
|
||||
partial_rotary_factor=1.0,
|
||||
vocab_size=32000,
|
||||
num_experts=8,
|
||||
@@ -1456,11 +1423,11 @@ if EXAONE4_AVAILABLE:
|
||||
num_hidden_layers=4,
|
||||
num_key_value_heads=2,
|
||||
rms_norm_eps=1e-5,
|
||||
rope_theta=1000000.0,
|
||||
tie_word_embeddings=True,
|
||||
use_cache=True,
|
||||
vocab_size=32000,
|
||||
attn_implementation="sdpa",
|
||||
pad_token_id=None,
|
||||
),
|
||||
)
|
||||
|
||||
@@ -1553,12 +1520,12 @@ def run_mini_model(
|
||||
"model_name, num_steps, lr, dtype, loss_atol, loss_rtol, logprobs_atol, logprobs_rtol, param_atol, param_rtol",
|
||||
[
|
||||
pytest.param(
|
||||
"mini_llama4",
|
||||
"mini_llama4", # llama4 requires slightly larger tolerances to pass this test after bug fix to llama4 in transformers v5.0.0
|
||||
32,
|
||||
1e-4,
|
||||
torch.float32,
|
||||
1e-8,
|
||||
1e-5,
|
||||
1e-3,
|
||||
5e-3,
|
||||
1e-5,
|
||||
5e-3,
|
||||
|
||||
@@ -10,11 +10,14 @@ import torch
|
||||
import transformers
|
||||
|
||||
from packaging import version
|
||||
from test.utils import get_mllama_rope_config
|
||||
from test.utils import get_qwen3_vl_rope_config
|
||||
from transformers import AutoModelForCausalLM
|
||||
from transformers import PretrainedConfig
|
||||
from transformers import PreTrainedModel
|
||||
|
||||
from liger_kernel.transformers import LigerBlockSparseTop2MLP
|
||||
from liger_kernel.transformers import LigerExperts
|
||||
from liger_kernel.transformers import LigerGEGLUMLP
|
||||
from liger_kernel.transformers import LigerPhi3SwiGLUMLP
|
||||
from liger_kernel.transformers import LigerQwen3MoeSwiGLUMLP
|
||||
@@ -22,43 +25,32 @@ from liger_kernel.transformers import LigerRMSNorm
|
||||
from liger_kernel.transformers import LigerSwiGLUMLP
|
||||
from liger_kernel.transformers import monkey_patch
|
||||
from liger_kernel.transformers.layer_norm import LigerLayerNorm
|
||||
from liger_kernel.transformers.model.falcon_h1 import lce_forward as falcon_h1_lce_forward
|
||||
from liger_kernel.transformers.model.gemma import lce_forward as gemma_lce_forward
|
||||
from liger_kernel.transformers.model.gemma2 import lce_forward as gemma2_lce_forward
|
||||
from liger_kernel.transformers.model.llama import lce_forward as llama_lce_forward
|
||||
from liger_kernel.transformers.model.mistral import lce_forward as mistral_lce_forward
|
||||
from liger_kernel.transformers.model.mixtral import lce_forward as mixtral_lce_forward
|
||||
from liger_kernel.transformers.model.mllama import lce_forward as mllama_lce_forward
|
||||
from liger_kernel.transformers.model.paligemma import lce_forward as paligemma_lce_forward
|
||||
from liger_kernel.transformers.model.phi3 import lce_forward as phi3_lce_forward
|
||||
from liger_kernel.transformers.model.qwen2 import lce_forward as qwen2_lce_forward
|
||||
from liger_kernel.transformers.model.qwen3_next import lce_forward as qwen3_next_lce_forward
|
||||
from liger_kernel.transformers.model.smollm3 import lce_forward as smolllm3_lce_forward
|
||||
from liger_kernel.transformers.monkey_patch import MODEL_TYPE_TO_APPLY_LIGER_FN
|
||||
from liger_kernel.transformers.monkey_patch import _apply_liger_kernel
|
||||
from liger_kernel.transformers.monkey_patch import _apply_liger_kernel_to_instance
|
||||
|
||||
# Import transformer version check
|
||||
# We only support transformers >= 4.52.0
|
||||
transformer_version = version.parse(transformers.__version__)
|
||||
SUPPORTED_TRANSFORMER_VERSION = "4.46.1"
|
||||
MIN_SUPPORTED_TRANSFORMERS_VERSION = version.parse("4.52.0")
|
||||
if transformer_version < MIN_SUPPORTED_TRANSFORMERS_VERSION:
|
||||
pytest.skip(
|
||||
f"tests require transformers >= {MIN_SUPPORTED_TRANSFORMERS_VERSION}, got {transformers.__version__}",
|
||||
allow_module_level=True,
|
||||
)
|
||||
|
||||
# Import forward functions based on transformer version
|
||||
if transformer_version >= version.parse(SUPPORTED_TRANSFORMER_VERSION):
|
||||
from liger_kernel.transformers.model.falcon_h1 import lce_forward as falcon_h1_lce_forward
|
||||
from liger_kernel.transformers.model.gemma import lce_forward as gemma_lce_forward
|
||||
from liger_kernel.transformers.model.gemma2 import lce_forward as gemma2_lce_forward
|
||||
from liger_kernel.transformers.model.llama import lce_forward as llama_lce_forward
|
||||
from liger_kernel.transformers.model.mistral import lce_forward as mistral_lce_forward
|
||||
from liger_kernel.transformers.model.mixtral import lce_forward as mixtral_lce_forward
|
||||
from liger_kernel.transformers.model.mllama import lce_forward as mllama_lce_forward
|
||||
from liger_kernel.transformers.model.paligemma import lce_forward as paligemma_lce_forward
|
||||
from liger_kernel.transformers.model.phi3 import lce_forward as phi3_lce_forward
|
||||
from liger_kernel.transformers.model.qwen2 import lce_forward as qwen2_lce_forward
|
||||
from liger_kernel.transformers.model.qwen3_next import lce_forward as qwen3_next_lce_forward
|
||||
from liger_kernel.transformers.model.smollm3 import lce_forward as smolllm3_lce_forward
|
||||
else:
|
||||
from liger_kernel.transformers.model.gemma import lce_forward_deprecated as gemma_lce_forward
|
||||
from liger_kernel.transformers.model.gemma2 import lce_forward_deprecated as gemma2_lce_forward
|
||||
from liger_kernel.transformers.model.llama import lce_forward_deprecated as llama_lce_forward
|
||||
from liger_kernel.transformers.model.mistral import (
|
||||
lce_forward as mistral_lce_forward, # mistral doesn't have deprecated version
|
||||
)
|
||||
from liger_kernel.transformers.model.mixtral import lce_forward_deprecated as mixtral_lce_forward
|
||||
from liger_kernel.transformers.model.mllama import lce_forward_deprecated as mllama_lce_forward
|
||||
from liger_kernel.transformers.model.paligemma import lce_forward_deprecated as paligemma_lce_forward
|
||||
from liger_kernel.transformers.model.phi3 import lce_forward_deprecated as phi3_lce_forward
|
||||
from liger_kernel.transformers.model.qwen2 import lce_forward_deprecated as qwen2_lce_forward
|
||||
from liger_kernel.transformers.model.qwen3_next import (
|
||||
lce_forward as qwen3_next_lce_forward, # qwen3_next doesn't have deprecated version
|
||||
)
|
||||
IS_TRANSFORMERS_V5_OR_LATER = transformer_version >= version.parse("5.0.0")
|
||||
|
||||
|
||||
# Check if optional modules are available
|
||||
@@ -497,13 +489,9 @@ def test_apply_liger_kernel_to_instance_for_qwen3_vl_for_conditional_generation(
|
||||
rms_norm_eps=1e-6,
|
||||
use_cache=False,
|
||||
tie_word_embeddings=True,
|
||||
rope_theta=1000000.0,
|
||||
rope_scaling=dict(
|
||||
type="mrope",
|
||||
mrope_section=[16, 24, 24],
|
||||
),
|
||||
attention_dropout=0.0,
|
||||
attention_bias=False,
|
||||
**get_qwen3_vl_rope_config(), # Version-aware rope configuration
|
||||
).to_dict(),
|
||||
)
|
||||
dummy_model_instance = Qwen3VLForConditionalGeneration._from_config(config)
|
||||
@@ -598,13 +586,9 @@ def test_apply_liger_kernel_to_instance_for_qwen3_vl():
|
||||
rms_norm_eps=1e-6,
|
||||
use_cache=False,
|
||||
tie_word_embeddings=True,
|
||||
rope_theta=1000000.0,
|
||||
rope_scaling=dict(
|
||||
type="mrope",
|
||||
mrope_section=[16, 24, 24],
|
||||
),
|
||||
attention_dropout=0.0,
|
||||
attention_bias=False,
|
||||
**get_qwen3_vl_rope_config(), # Version-aware rope configuration
|
||||
).to_dict(),
|
||||
)
|
||||
dummy_model_instance = Qwen3VLModel._from_config(config)
|
||||
@@ -675,13 +659,9 @@ def test_apply_liger_kernel_to_instance_for_qwen3_vl_text():
|
||||
rms_norm_eps=1e-6,
|
||||
use_cache=False,
|
||||
tie_word_embeddings=True,
|
||||
rope_theta=1000000.0,
|
||||
rope_scaling=dict(
|
||||
type="mrope",
|
||||
mrope_section=[16, 24, 24],
|
||||
),
|
||||
attention_dropout=0.0,
|
||||
attention_bias=False,
|
||||
**get_qwen3_vl_rope_config(), # Version-aware rope configuration
|
||||
)
|
||||
dummy_model_instance = Qwen3VLTextModel._from_config(config)
|
||||
|
||||
@@ -771,11 +751,6 @@ def test_apply_liger_kernel_to_instance_for_qwen3_vl_moe_for_conditional_generat
|
||||
rms_norm_eps=1e-6,
|
||||
use_cache=False,
|
||||
tie_word_embeddings=True,
|
||||
rope_theta=1000000.0,
|
||||
rope_scaling=dict(
|
||||
type="mrope",
|
||||
mrope_section=[16, 24, 24],
|
||||
),
|
||||
attention_dropout=0.0,
|
||||
attention_bias=False,
|
||||
decoder_sparse_step=1,
|
||||
@@ -783,6 +758,8 @@ def test_apply_liger_kernel_to_instance_for_qwen3_vl_moe_for_conditional_generat
|
||||
num_experts_per_tok=2,
|
||||
num_experts=4,
|
||||
mlp_only_layers=[],
|
||||
pad_token_id=None,
|
||||
**get_qwen3_vl_rope_config(), # Version-aware rope configuration
|
||||
).to_dict(),
|
||||
)
|
||||
dummy_model_instance = Qwen3VLMoeForConditionalGeneration._from_config(config)
|
||||
@@ -877,11 +854,6 @@ def test_apply_liger_kernel_to_instance_for_qwen3_vl_moe():
|
||||
rms_norm_eps=1e-6,
|
||||
use_cache=False,
|
||||
tie_word_embeddings=True,
|
||||
rope_theta=1000000.0,
|
||||
rope_scaling=dict(
|
||||
type="mrope",
|
||||
mrope_section=[16, 24, 24],
|
||||
),
|
||||
attention_dropout=0.0,
|
||||
attention_bias=False,
|
||||
decoder_sparse_step=1,
|
||||
@@ -889,6 +861,8 @@ def test_apply_liger_kernel_to_instance_for_qwen3_vl_moe():
|
||||
num_experts_per_tok=2,
|
||||
num_experts=4,
|
||||
mlp_only_layers=[],
|
||||
pad_token_id=None,
|
||||
**get_qwen3_vl_rope_config(), # Version-aware rope configuration
|
||||
).to_dict(),
|
||||
)
|
||||
dummy_model_instance = Qwen3VLMoeModel._from_config(config)
|
||||
@@ -959,11 +933,6 @@ def test_apply_liger_kernel_to_instance_for_qwen3_vl_moe_text():
|
||||
rms_norm_eps=1e-6,
|
||||
use_cache=False,
|
||||
tie_word_embeddings=True,
|
||||
rope_theta=1000000.0,
|
||||
rope_scaling=dict(
|
||||
type="mrope",
|
||||
mrope_section=[16, 24, 24],
|
||||
),
|
||||
attention_dropout=0.0,
|
||||
attention_bias=False,
|
||||
decoder_sparse_step=1,
|
||||
@@ -971,6 +940,8 @@ def test_apply_liger_kernel_to_instance_for_qwen3_vl_moe_text():
|
||||
num_experts_per_tok=2,
|
||||
num_experts=4,
|
||||
mlp_only_layers=[],
|
||||
pad_token_id=None,
|
||||
**get_qwen3_vl_rope_config(), # Version-aware rope configuration
|
||||
)
|
||||
dummy_model_instance = Qwen3VLMoeTextModel._from_config(config)
|
||||
|
||||
@@ -1106,13 +1077,7 @@ def test_apply_liger_kernel_to_instance_for_mllama_for_conditional_generation():
|
||||
intermediate_size=64,
|
||||
hidden_act="silu",
|
||||
num_hidden_layers=2,
|
||||
rope_scaling=dict(
|
||||
factor=8.0,
|
||||
high_freq_factor=4.0,
|
||||
low_freq_factor=1.0,
|
||||
original_max_position_embeddings=8192,
|
||||
rope_type="llama3",
|
||||
),
|
||||
**get_mllama_rope_config(), # Version-aware rope configuration
|
||||
),
|
||||
vision_config=transformers.models.mllama.configuration_mllama.MllamaVisionConfig(
|
||||
rms_norm_eps=1e-5,
|
||||
@@ -1204,13 +1169,7 @@ def test_apply_liger_kernel_to_instance_for_mllama_for_causal_lm():
|
||||
intermediate_size=64,
|
||||
hidden_act="silu",
|
||||
num_hidden_layers=2,
|
||||
rope_scaling=dict(
|
||||
factor=8.0,
|
||||
high_freq_factor=4.0,
|
||||
low_freq_factor=1.0,
|
||||
original_max_position_embeddings=8192,
|
||||
rope_type="llama3",
|
||||
),
|
||||
**get_mllama_rope_config(), # Version-aware rope configuration
|
||||
)
|
||||
|
||||
dummy_model_instance = MllamaForCausalLM._from_config(config)
|
||||
@@ -1319,6 +1278,7 @@ def test_apply_liger_kernel_to_instance_for_llama4_for_conditional_generation():
|
||||
num_hidden_layers=2,
|
||||
vision_output_dim=64,
|
||||
),
|
||||
pad_token_id=None,
|
||||
)
|
||||
dummy_model_instance = Llama4ForConditionalGeneration._from_config(config)
|
||||
|
||||
@@ -1386,10 +1346,6 @@ def test_apply_liger_kernel_to_instance_for_llama4_for_conditional_generation():
|
||||
pytest.fail(f"An exception occured in extra_expr: {type(e).__name__} - {e}")
|
||||
|
||||
|
||||
@pytest.mark.skipif(
|
||||
transformer_version < version.parse("4.49.0"),
|
||||
reason="fused linear cross entropy patch doesn't work on mistral in transformers<4.49.0",
|
||||
)
|
||||
def test_apply_liger_kernel_to_instance_for_mistral():
|
||||
# Ensure any monkey patching is cleaned up for subsequent tests
|
||||
with patch("transformers.models.mistral.modeling_mistral"):
|
||||
@@ -1449,8 +1405,11 @@ def test_apply_liger_kernel_to_instance_for_mixtral():
|
||||
assert inspect.getsource(dummy_model_instance.forward) != inspect.getsource(mixtral_lce_forward)
|
||||
assert inspect.getsource(dummy_model_instance.model.norm.forward) != inspect.getsource(LigerRMSNorm.forward)
|
||||
for layer in dummy_model_instance.model.layers:
|
||||
for expert in layer.block_sparse_moe.experts:
|
||||
assert inspect.getsource(expert.forward) != inspect.getsource(LigerBlockSparseTop2MLP.forward)
|
||||
if IS_TRANSFORMERS_V5_OR_LATER:
|
||||
assert inspect.getsource(layer.mlp.experts.forward) != inspect.getsource(LigerExperts.forward)
|
||||
else:
|
||||
for expert in layer.block_sparse_moe.experts:
|
||||
assert inspect.getsource(expert.forward) != inspect.getsource(LigerBlockSparseTop2MLP.forward)
|
||||
assert inspect.getsource(layer.input_layernorm.forward) != inspect.getsource(LigerRMSNorm.forward)
|
||||
assert inspect.getsource(layer.post_attention_layernorm.forward) != inspect.getsource(LigerRMSNorm.forward)
|
||||
|
||||
@@ -1461,8 +1420,11 @@ def test_apply_liger_kernel_to_instance_for_mixtral():
|
||||
assert inspect.getsource(dummy_model_instance.forward) == inspect.getsource(mixtral_lce_forward)
|
||||
assert inspect.getsource(dummy_model_instance.model.norm.forward) == inspect.getsource(LigerRMSNorm.forward)
|
||||
for layer in dummy_model_instance.model.layers:
|
||||
for expert in layer.block_sparse_moe.experts:
|
||||
assert inspect.getsource(expert.forward) == inspect.getsource(LigerBlockSparseTop2MLP.forward)
|
||||
if IS_TRANSFORMERS_V5_OR_LATER:
|
||||
assert inspect.getsource(layer.mlp.experts.forward) == inspect.getsource(LigerExperts.forward)
|
||||
else:
|
||||
for expert in layer.block_sparse_moe.experts:
|
||||
assert inspect.getsource(expert.forward) == inspect.getsource(LigerBlockSparseTop2MLP.forward)
|
||||
assert inspect.getsource(layer.input_layernorm.forward) == inspect.getsource(LigerRMSNorm.forward)
|
||||
assert inspect.getsource(layer.post_attention_layernorm.forward) == inspect.getsource(LigerRMSNorm.forward)
|
||||
|
||||
@@ -1862,7 +1824,11 @@ def test_apply_liger_kernel_to_instance_for_qwen3_moe():
|
||||
assert inspect.getsource(dummy_model_instance.forward) != inspect.getsource(qwen3_moe_lce_forward)
|
||||
assert inspect.getsource(dummy_model_instance.model.norm.forward) != inspect.getsource(LigerRMSNorm.forward)
|
||||
for layer in dummy_model_instance.model.layers:
|
||||
assert inspect.getsource(layer.mlp.forward) != inspect.getsource(LigerQwen3MoeSwiGLUMLP.forward)
|
||||
if IS_TRANSFORMERS_V5_OR_LATER:
|
||||
assert inspect.getsource(layer.mlp.experts.forward) != inspect.getsource(LigerExperts.forward)
|
||||
else:
|
||||
for expert in layer.mlp.experts:
|
||||
assert inspect.getsource(expert.forward) != inspect.getsource(LigerQwen3MoeSwiGLUMLP.forward)
|
||||
assert inspect.getsource(layer.input_layernorm.forward) != inspect.getsource(LigerRMSNorm.forward)
|
||||
assert inspect.getsource(layer.post_attention_layernorm.forward) != inspect.getsource(LigerRMSNorm.forward)
|
||||
|
||||
@@ -1873,8 +1839,11 @@ def test_apply_liger_kernel_to_instance_for_qwen3_moe():
|
||||
assert inspect.getsource(dummy_model_instance.forward) == inspect.getsource(qwen3_moe_lce_forward)
|
||||
assert inspect.getsource(dummy_model_instance.model.norm.forward) == inspect.getsource(LigerRMSNorm.forward)
|
||||
for layer in dummy_model_instance.model.layers:
|
||||
for mlp_expert in layer.mlp.experts:
|
||||
assert inspect.getsource(mlp_expert.forward) == inspect.getsource(LigerQwen3MoeSwiGLUMLP.forward)
|
||||
if IS_TRANSFORMERS_V5_OR_LATER:
|
||||
assert inspect.getsource(layer.mlp.experts.forward) == inspect.getsource(LigerExperts.forward)
|
||||
else:
|
||||
for expert in layer.mlp.experts:
|
||||
assert inspect.getsource(expert.forward) == inspect.getsource(LigerQwen3MoeSwiGLUMLP.forward)
|
||||
assert inspect.getsource(layer.input_layernorm.forward) == inspect.getsource(LigerRMSNorm.forward)
|
||||
assert inspect.getsource(layer.post_attention_layernorm.forward) == inspect.getsource(LigerRMSNorm.forward)
|
||||
|
||||
@@ -2596,6 +2565,7 @@ def test_apply_liger_kernel_to_instance_for_glm4v():
|
||||
"hidden_size": 32,
|
||||
"intermediate_size": 64,
|
||||
"hidden_act": "silu",
|
||||
"pad_token_id": None,
|
||||
},
|
||||
vision_config={
|
||||
"num_hidden_layers": 2,
|
||||
@@ -2703,8 +2673,11 @@ def test_apply_liger_kernel_to_instance_for_glm4v_moe():
|
||||
LigerRMSNormForGlm4.forward
|
||||
)
|
||||
if decoder_layer.mlp.experts is not None:
|
||||
for expert in decoder_layer.mlp.experts:
|
||||
assert inspect.getsource(expert.forward) != inspect.getsource(LigerSwiGLUMLP.forward)
|
||||
if IS_TRANSFORMERS_V5_OR_LATER:
|
||||
assert inspect.getsource(decoder_layer.mlp.experts.forward) != inspect.getsource(LigerExperts.forward)
|
||||
else:
|
||||
for expert in decoder_layer.mlp.experts:
|
||||
assert inspect.getsource(expert.forward) != inspect.getsource(LigerSwiGLUMLP.forward)
|
||||
if decoder_layer.mlp.shared_experts is not None:
|
||||
assert inspect.getsource(decoder_layer.mlp.shared_experts.forward) != inspect.getsource(
|
||||
LigerSwiGLUMLP.forward
|
||||
@@ -2739,8 +2712,13 @@ def test_apply_liger_kernel_to_instance_for_glm4v_moe():
|
||||
LigerRMSNormForGlm4.forward
|
||||
)
|
||||
if getattr(decoder_layer.mlp, "experts", None) is not None:
|
||||
for expert in decoder_layer.mlp.experts:
|
||||
assert inspect.getsource(expert.forward) == inspect.getsource(LigerSwiGLUMLP.forward)
|
||||
if IS_TRANSFORMERS_V5_OR_LATER:
|
||||
assert inspect.getsource(decoder_layer.mlp.experts.forward) == inspect.getsource(
|
||||
LigerExperts.forward
|
||||
)
|
||||
else:
|
||||
for expert in decoder_layer.mlp.experts:
|
||||
assert inspect.getsource(expert.forward) == inspect.getsource(LigerSwiGLUMLP.forward)
|
||||
if getattr(decoder_layer.mlp, "shared_experts", None) is not None:
|
||||
assert inspect.getsource(decoder_layer.mlp.shared_experts.forward) == inspect.getsource(
|
||||
LigerSwiGLUMLP.forward
|
||||
@@ -2822,8 +2800,15 @@ def test_apply_liger_kernel_to_instance_for_qwen3_next():
|
||||
assert inspect.getsource(dummy_model_instance.model.norm.forward) != inspect.getsource(LigerRMSNorm.forward)
|
||||
for layer in dummy_model_instance.model.layers:
|
||||
if hasattr(layer, "mlp") and hasattr(layer.mlp, "experts"):
|
||||
for expert in layer.mlp.experts:
|
||||
assert inspect.getsource(expert.forward) != inspect.getsource(LigerQwen3MoeSwiGLUMLP.forward)
|
||||
if IS_TRANSFORMERS_V5_OR_LATER:
|
||||
assert inspect.getsource(layer.mlp.experts.forward) != inspect.getsource(LigerExperts.forward)
|
||||
else:
|
||||
for expert in layer.mlp.experts:
|
||||
assert inspect.getsource(expert.forward) != inspect.getsource(LigerQwen3MoeSwiGLUMLP.forward)
|
||||
if hasattr(layer.mlp, "shared_expert"):
|
||||
assert inspect.getsource(layer.mlp.shared_expert.forward) != inspect.getsource(
|
||||
LigerSwiGLUMLP.forward
|
||||
)
|
||||
else:
|
||||
assert inspect.getsource(layer.mlp.forward) != inspect.getsource(LigerQwen3MoeSwiGLUMLP.forward)
|
||||
|
||||
@@ -2838,8 +2823,11 @@ def test_apply_liger_kernel_to_instance_for_qwen3_next():
|
||||
assert inspect.getsource(dummy_model_instance.model.norm.forward) == inspect.getsource(LigerRMSNorm.forward)
|
||||
for layer in dummy_model_instance.model.layers:
|
||||
if hasattr(layer, "mlp") and hasattr(layer.mlp, "experts"):
|
||||
for expert in layer.mlp.experts:
|
||||
assert inspect.getsource(expert.forward) == inspect.getsource(LigerQwen3MoeSwiGLUMLP.forward)
|
||||
if IS_TRANSFORMERS_V5_OR_LATER:
|
||||
assert inspect.getsource(layer.mlp.experts.forward) == inspect.getsource(LigerExperts.forward)
|
||||
else:
|
||||
for expert in layer.mlp.experts:
|
||||
assert inspect.getsource(expert.forward) == inspect.getsource(LigerQwen3MoeSwiGLUMLP.forward)
|
||||
if hasattr(layer.mlp, "shared_expert"):
|
||||
assert inspect.getsource(layer.mlp.shared_expert.forward) == inspect.getsource(
|
||||
LigerSwiGLUMLP.forward
|
||||
@@ -2878,7 +2866,11 @@ def test_apply_liger_kernel_to_instance_for_hunyuan_v1_moe():
|
||||
assert inspect.getsource(dummy_model_instance.forward) != inspect.getsource(hunyuan_v1_moe_lce_forward)
|
||||
assert inspect.getsource(dummy_model_instance.model.norm.forward) != inspect.getsource(LigerRMSNorm.forward)
|
||||
for layer in dummy_model_instance.model.layers:
|
||||
assert inspect.getsource(layer.mlp.forward) != inspect.getsource(LigerQwen3MoeSwiGLUMLP.forward)
|
||||
if IS_TRANSFORMERS_V5_OR_LATER:
|
||||
assert inspect.getsource(layer.mlp.experts.forward) != inspect.getsource(LigerExperts.forward)
|
||||
else:
|
||||
for expert in layer.mlp.experts:
|
||||
assert inspect.getsource(expert.forward) != inspect.getsource(LigerQwen3MoeSwiGLUMLP.forward)
|
||||
assert inspect.getsource(layer.input_layernorm.forward) != inspect.getsource(LigerRMSNorm.forward)
|
||||
assert inspect.getsource(layer.post_attention_layernorm.forward) != inspect.getsource(LigerRMSNorm.forward)
|
||||
|
||||
@@ -2889,8 +2881,11 @@ def test_apply_liger_kernel_to_instance_for_hunyuan_v1_moe():
|
||||
assert inspect.getsource(dummy_model_instance.forward) == inspect.getsource(hunyuan_v1_moe_lce_forward)
|
||||
assert inspect.getsource(dummy_model_instance.model.norm.forward) == inspect.getsource(LigerRMSNorm.forward)
|
||||
for layer in dummy_model_instance.model.layers:
|
||||
for mlp_expert in layer.mlp.experts:
|
||||
assert inspect.getsource(mlp_expert.forward) == inspect.getsource(LigerQwen3MoeSwiGLUMLP.forward)
|
||||
if IS_TRANSFORMERS_V5_OR_LATER:
|
||||
assert inspect.getsource(layer.mlp.experts.forward) == inspect.getsource(LigerExperts.forward)
|
||||
else:
|
||||
for mlp_expert in layer.mlp.experts:
|
||||
assert inspect.getsource(mlp_expert.forward) == inspect.getsource(LigerQwen3MoeSwiGLUMLP.forward)
|
||||
assert inspect.getsource(layer.input_layernorm.forward) == inspect.getsource(LigerRMSNorm.forward)
|
||||
assert inspect.getsource(layer.post_attention_layernorm.forward) == inspect.getsource(LigerRMSNorm.forward)
|
||||
|
||||
|
||||
@@ -83,7 +83,7 @@ def test_correctness(
|
||||
cos, sin = rotary_emb(k1, pos_ids)
|
||||
|
||||
# validate forward pass
|
||||
hf_q, hf_k = apply_rotary_pos_emb(q1, k1, cos, sin, pos_ids)
|
||||
hf_q, hf_k = apply_rotary_pos_emb(q1, k1, cos, sin)
|
||||
tt_q, tt_k = liger_rotary_pos_emb(q2, k2, cos, sin)
|
||||
assert torch.allclose(hf_q, tt_q, atol=atol, rtol=rtol)
|
||||
assert torch.allclose(hf_k, tt_k, atol=atol, rtol=rtol)
|
||||
|
||||
@@ -1,18 +1,29 @@
|
||||
import pytest
|
||||
import torch
|
||||
import transformers
|
||||
|
||||
from packaging import version
|
||||
from test.utils import supports_bfloat16
|
||||
from transformers.models.llama.configuration_llama import LlamaConfig
|
||||
from transformers.models.llama.modeling_llama import LlamaMLP
|
||||
from transformers.models.mixtral.configuration_mixtral import MixtralConfig
|
||||
from transformers.models.phi3.configuration_phi3 import Phi3Config
|
||||
from transformers.models.phi3.modeling_phi3 import Phi3MLP
|
||||
|
||||
from liger_kernel.ops.swiglu import LigerSiLUMulFunction
|
||||
from liger_kernel.transformers.functional import liger_swiglu
|
||||
from liger_kernel.transformers.swiglu import LigerBlockSparseTop2MLP
|
||||
from liger_kernel.transformers.swiglu import LigerExperts
|
||||
from liger_kernel.transformers.swiglu import LigerPhi3SwiGLUMLP
|
||||
from liger_kernel.transformers.swiglu import LigerSwiGLUMLP
|
||||
from liger_kernel.utils import infer_device
|
||||
|
||||
IS_TRANSFORMERS_V5_OR_LATER = version.parse(transformers.__version__) >= version.parse("5.0.0")
|
||||
if IS_TRANSFORMERS_V5_OR_LATER:
|
||||
from transformers.models.mixtral.modeling_mixtral import MixtralExperts
|
||||
else:
|
||||
from transformers.models.mixtral.modeling_mixtral import MixtralBlockSparseTop2MLP
|
||||
|
||||
device = infer_device()
|
||||
|
||||
LLAMA_CONFIG = LlamaConfig(
|
||||
@@ -104,6 +115,188 @@ def test_correctness_llamamlp(bsz, seq_len, hidden_size, intermediate_size, dtyp
|
||||
assert torch.allclose(x1.grad, x2.grad, atol=atol, rtol=rtol)
|
||||
|
||||
|
||||
@pytest.mark.skipif(IS_TRANSFORMERS_V5_OR_LATER, reason="Skip for transformers >= v5.0.0")
|
||||
@pytest.mark.parametrize(
|
||||
"bsz, seq_len, hidden_size, intermediate_size",
|
||||
[
|
||||
(2, 256, 256, 512),
|
||||
# weird shapes
|
||||
(6, 42, 123, 431),
|
||||
],
|
||||
)
|
||||
@pytest.mark.parametrize(
|
||||
"dtype, atol, rtol",
|
||||
[
|
||||
# atol is for small values: they have more difference, so set atol higher
|
||||
# rtol is for larger values: they are very close, so set rtol lower
|
||||
(torch.float32, 1e-0, 1e-5),
|
||||
# TODO: we should find a better way to tune this. 1e4 is too large apparently
|
||||
pytest.param(
|
||||
torch.bfloat16,
|
||||
1e4,
|
||||
1e-2,
|
||||
marks=pytest.mark.skipif(not supports_bfloat16(), reason="bfloat16 not supported on this GPU"),
|
||||
),
|
||||
],
|
||||
)
|
||||
def test_correctness_mixtralblocksparsetop2mlp(bsz, seq_len, hidden_size, intermediate_size, dtype, atol, rtol):
|
||||
MIXTRAL_CONFIG = MixtralConfig(
|
||||
num_local_experts=8,
|
||||
hidden_size=hidden_size,
|
||||
intermediate_size=intermediate_size,
|
||||
hidden_act="silu",
|
||||
num_experts_per_tok=2,
|
||||
)
|
||||
|
||||
_input = torch.randn(bsz, seq_len, hidden_size, device=device, dtype=dtype)
|
||||
x1 = _input.clone().requires_grad_(True)
|
||||
x2 = _input.clone().requires_grad_(True)
|
||||
|
||||
# initialize weights
|
||||
G = torch.randn(hidden_size, intermediate_size, device=device, dtype=dtype)
|
||||
U = torch.randn(intermediate_size, hidden_size, device=device, dtype=dtype)
|
||||
D = torch.randn(hidden_size, intermediate_size, device=device, dtype=dtype)
|
||||
|
||||
mixtral_blocksparsetop2mlp = MixtralBlockSparseTop2MLP(config=MIXTRAL_CONFIG).to(device).to(dtype)
|
||||
mixtral_blocksparsetop2mlp.w1.weight.data = G.T
|
||||
mixtral_blocksparsetop2mlp.w2.weight.data = U.T
|
||||
mixtral_blocksparsetop2mlp.w3.weight.data = D.T
|
||||
|
||||
liger_blocksparsetop2mlp = LigerBlockSparseTop2MLP(config=MIXTRAL_CONFIG).to(device).to(dtype)
|
||||
liger_blocksparsetop2mlp.w1.weight.data = G.T
|
||||
liger_blocksparsetop2mlp.w2.weight.data = U.T
|
||||
liger_blocksparsetop2mlp.w3.weight.data = D.T
|
||||
|
||||
y1 = mixtral_blocksparsetop2mlp(x1)
|
||||
y2 = liger_blocksparsetop2mlp(x2)
|
||||
|
||||
assert torch.allclose(y1, y2, atol=atol, rtol=rtol)
|
||||
|
||||
dy = torch.randn_like(y1)
|
||||
|
||||
y1.backward(dy.clone(), retain_graph=True)
|
||||
y2.backward(dy.clone(), retain_graph=True)
|
||||
|
||||
assert torch.allclose(
|
||||
mixtral_blocksparsetop2mlp.w1.weight.grad,
|
||||
liger_blocksparsetop2mlp.w1.weight.grad,
|
||||
atol=atol,
|
||||
rtol=rtol,
|
||||
)
|
||||
assert torch.allclose(
|
||||
mixtral_blocksparsetop2mlp.w2.weight.grad,
|
||||
liger_blocksparsetop2mlp.w2.weight.grad,
|
||||
atol=atol,
|
||||
rtol=rtol,
|
||||
)
|
||||
assert torch.allclose(
|
||||
mixtral_blocksparsetop2mlp.w3.weight.grad,
|
||||
liger_blocksparsetop2mlp.w3.weight.grad,
|
||||
atol=atol,
|
||||
rtol=rtol,
|
||||
)
|
||||
|
||||
assert torch.allclose(x1.grad, x2.grad, atol=atol, rtol=rtol)
|
||||
|
||||
|
||||
@pytest.mark.skipif(not IS_TRANSFORMERS_V5_OR_LATER, reason="Skip for transformers < v5.0.0")
|
||||
@pytest.mark.parametrize(
|
||||
"bsz, seq_len, hidden_size, intermediate_size",
|
||||
[
|
||||
(2, 256, 256, 512),
|
||||
# weird shapes
|
||||
(6, 42, 123, 431),
|
||||
],
|
||||
)
|
||||
@pytest.mark.parametrize(
|
||||
"dtype, atol, rtol",
|
||||
[
|
||||
# atol is for small values: they have more difference, so set atol higher
|
||||
# rtol is for larger values: they are very close, so set rtol lower
|
||||
(torch.float32, 1e-0, 1e-5),
|
||||
# TODO: we should find a better way to tune this. 1e4 is too large apparently
|
||||
pytest.param(
|
||||
torch.bfloat16,
|
||||
1e4,
|
||||
1e-2,
|
||||
marks=pytest.mark.skipif(not supports_bfloat16(), reason="bfloat16 not supported on this GPU"),
|
||||
),
|
||||
],
|
||||
)
|
||||
def test_correctness_mixtralexperts(bsz, seq_len, hidden_size, intermediate_size, dtype, atol, rtol):
|
||||
MIXTRAL_CONFIG = MixtralConfig(
|
||||
num_local_experts=8,
|
||||
hidden_size=hidden_size,
|
||||
intermediate_size=intermediate_size,
|
||||
experts_implementation="eager",
|
||||
hidden_act="silu",
|
||||
num_experts_per_tok=2,
|
||||
)
|
||||
|
||||
_input = torch.randn(bsz * seq_len, hidden_size, device=device, dtype=dtype)
|
||||
|
||||
x1 = _input.clone().requires_grad_(True)
|
||||
x2 = _input.clone().requires_grad_(True)
|
||||
|
||||
# match shape: (num_experts, 2 * intermediate_dim, hidden_dim)
|
||||
GU = torch.randn(
|
||||
MIXTRAL_CONFIG.num_local_experts,
|
||||
2 * intermediate_size,
|
||||
hidden_size,
|
||||
device=device,
|
||||
dtype=dtype,
|
||||
requires_grad=True,
|
||||
)
|
||||
# match shape: (num_experts, hidden_dim, intermediate_dim)
|
||||
D = torch.randn(
|
||||
MIXTRAL_CONFIG.num_local_experts, hidden_size, intermediate_size, device=device, dtype=dtype, requires_grad=True
|
||||
)
|
||||
|
||||
# Generate random router logits and do topk
|
||||
router_logits = torch.randn(bsz * seq_len, MIXTRAL_CONFIG.num_local_experts, device=device, dtype=dtype)
|
||||
router_logits = router_logits.softmax(dim=-1)
|
||||
top_k_weights, top_k_index = router_logits.topk(k=MIXTRAL_CONFIG.num_experts_per_tok, dim=-1)
|
||||
top_k_weights = top_k_weights / (top_k_weights.sum(dim=-1, keepdim=True) + 1e-9)
|
||||
|
||||
mixtral_experts = MixtralExperts(config=MIXTRAL_CONFIG).to(device).to(dtype)
|
||||
mixtral_experts.gate_up_proj.data = GU.clone().detach()
|
||||
mixtral_experts.down_proj.data = D.clone().detach()
|
||||
|
||||
liger_experts = LigerExperts(config=MIXTRAL_CONFIG).to(device).to(dtype)
|
||||
liger_experts.gate_up_proj.data = GU.clone().detach()
|
||||
liger_experts.down_proj.data = D.clone().detach()
|
||||
|
||||
mixtral_experts.gate_up_proj.requires_grad_()
|
||||
mixtral_experts.down_proj.requires_grad_()
|
||||
liger_experts.gate_up_proj.requires_grad_()
|
||||
liger_experts.down_proj.requires_grad_()
|
||||
|
||||
y1 = mixtral_experts(x1, top_k_index, top_k_weights)
|
||||
y2 = liger_experts(x2, top_k_index, top_k_weights)
|
||||
|
||||
assert torch.allclose(y1, y2, atol=atol, rtol=rtol)
|
||||
|
||||
dy = torch.randn_like(y1)
|
||||
|
||||
y1.backward(dy.clone(), retain_graph=True)
|
||||
y2.backward(dy.clone(), retain_graph=True)
|
||||
|
||||
assert torch.allclose(
|
||||
mixtral_experts.gate_up_proj.grad,
|
||||
liger_experts.gate_up_proj.grad,
|
||||
atol=atol,
|
||||
rtol=rtol,
|
||||
)
|
||||
assert torch.allclose(
|
||||
mixtral_experts.down_proj.grad,
|
||||
liger_experts.down_proj.grad,
|
||||
atol=atol,
|
||||
rtol=rtol,
|
||||
)
|
||||
|
||||
assert torch.allclose(x1.grad, x2.grad, atol=atol, rtol=rtol)
|
||||
|
||||
|
||||
@pytest.mark.parametrize(
|
||||
"bsz, seq_len, hidden_size, intermediate_size",
|
||||
[
|
||||
|
||||
@@ -5,6 +5,7 @@ def test_import_from_root():
|
||||
try:
|
||||
from liger_kernel.transformers import LigerBlockSparseTop2MLP # noqa: F401
|
||||
from liger_kernel.transformers import LigerCrossEntropyLoss # noqa: F401
|
||||
from liger_kernel.transformers import LigerExperts # noqa: F401
|
||||
from liger_kernel.transformers import LigerFusedLinearCrossEntropyLoss # noqa: F401
|
||||
from liger_kernel.transformers import LigerGEGLUMLP # noqa: F401
|
||||
from liger_kernel.transformers import LigerLayerNorm # noqa: F401
|
||||
|
||||
+61
-2
@@ -31,6 +31,64 @@ from liger_kernel.utils import infer_device
|
||||
|
||||
device = infer_device()
|
||||
|
||||
# =============================================================================
|
||||
# Transformers Version Compatibility Utilities
|
||||
# =============================================================================
|
||||
# These utilities help maintain backward compatibility across different
|
||||
# versions of the transformers library (v4.52.0, v4.57.6, v5.0.0+).
|
||||
|
||||
TRANSFORMERS_VERSION = version.parse(transformers.__version__)
|
||||
TRANSFORMERS_V5 = version.parse("5.0.0")
|
||||
|
||||
|
||||
def is_transformers_v5_or_later() -> bool:
|
||||
"""Check if the installed transformers version is 5.0.0 or later."""
|
||||
return TRANSFORMERS_VERSION >= TRANSFORMERS_V5
|
||||
|
||||
|
||||
def get_mllama_rope_config() -> dict:
|
||||
"""
|
||||
Get the correct rope configuration for MLlama models.
|
||||
|
||||
In transformers v4.x: requires explicit rope_scaling with llama3 rope_type
|
||||
In transformers v5.0+: uses defaults, no explicit config needed
|
||||
|
||||
Returns:
|
||||
dict: Configuration dictionary with rope_scaling for v4.x, empty for v5.0+
|
||||
"""
|
||||
if is_transformers_v5_or_later():
|
||||
return {}
|
||||
return {
|
||||
"rope_scaling": {
|
||||
"factor": 8.0,
|
||||
"high_freq_factor": 4.0,
|
||||
"low_freq_factor": 1.0,
|
||||
"original_max_position_embeddings": 8192,
|
||||
"rope_type": "llama3",
|
||||
},
|
||||
}
|
||||
|
||||
|
||||
def get_qwen3_vl_rope_config() -> dict:
|
||||
"""
|
||||
Get the correct rope configuration for Qwen3-VL models.
|
||||
|
||||
In transformers v4.x: requires rope_scaling with type="mrope"
|
||||
In transformers v5.0+: uses defaults, no explicit config needed
|
||||
|
||||
Returns:
|
||||
dict: Configuration dictionary with rope_scaling for v4.x, empty for v5.0+
|
||||
"""
|
||||
if is_transformers_v5_or_later():
|
||||
return {}
|
||||
return {
|
||||
"rope_theta": 1000000.0,
|
||||
"rope_scaling": {
|
||||
"type": "mrope",
|
||||
"mrope_section": [16, 24, 24],
|
||||
},
|
||||
}
|
||||
|
||||
|
||||
def set_seed(seed=42):
|
||||
"""
|
||||
@@ -620,11 +678,12 @@ def revert_liger_kernel_to_llava(model_config: MiniModelConfig):
|
||||
Revert all Liger kernel patches applied to llava.
|
||||
"""
|
||||
|
||||
from transformers.models.clip import modeling_clip
|
||||
from transformers.models.llama import modeling_llama
|
||||
from transformers.models.llava import modeling_llava
|
||||
|
||||
importlib.reload(modeling_clip)
|
||||
# Note: Do NOT reload modeling_clip as it breaks CLIPVisionModel's
|
||||
# output_hidden_states functionality in transformers v5.
|
||||
# Liger kernel does not patch modeling_clip when model=None.
|
||||
importlib.reload(modeling_llava)
|
||||
importlib.reload(modeling_llama)
|
||||
|
||||
|
||||
Reference in New Issue
Block a user