sgl-project/sglang · error · ValueError
video token dim {int(rows.shape[-1])} != patch volume * chan
Error message
video token dim {int(rows.shape[-1])} != patch volume * channel {expected_dim} for latent_shape={list(latent_shape)}, patch_size={[pt, ph, pw]} What it means
minimax_h3_unpatchify_video_tokens reconstructs a latent from token rows and checks that the per-token feature dim equals pt*ph*pw*channel as implied by latent_shape and patch_size. A mismatch means the rows tensor was produced with a different patch size, channel count, or latent shape than declared, so the inverse einsum would silently corrupt data if allowed.
Source
Thrown at python/sglang/multimodal_gen/runtime/pipelines_core/stages/model_specific_stages/minimax_h3/packed_tokens.py:57
packed = latent.reshape(batch, channel, t, pt, h, ph, w, pw)
packed = torch.einsum("nctrhpwq->nthwcrpq", packed)
return packed.reshape(batch * t * h * w, channel * pt * ph * pw).contiguous()
def minimax_h3_unpatchify_video_tokens(
rows: torch.Tensor,
*,
latent_shape: Sequence[int],
patch_size: Sequence[int],
) -> torch.Tensor:
"""Unpack DiT video token rows into SGLang latent [B,C,T,H,W]."""
_rank(rows, "video token rows", 2)
t, h, w, channel = _int_tuple(latent_shape, "latent_shape", 4)
pt, ph, pw = _int_tuple(patch_size, "patch_size", 3)
expected_dim = pt * ph * pw * channel
if int(rows.shape[-1]) != expected_dim:
raise ValueError(
f"video token dim {int(rows.shape[-1])} != patch volume * channel "
f"{expected_dim} for latent_shape={list(latent_shape)}, "
f"patch_size={[pt, ph, pw]}"
)
rows_per_sample = t * h * w
if int(rows.shape[0]) % rows_per_sample:
raise ValueError(
f"video rows {int(rows.shape[0])} must be divisible by t*h*w "
f"{rows_per_sample} for latent_shape={list(latent_shape)}"
)
packed = rows.reshape(-1, t, h, w, channel, pt, ph, pw)
latent = torch.einsum("nthwcrpq->nctrhpwq", packed)
return latent.reshape(-1, channel, t * pt, h * ph, w * pw).contiguous()
def minimax_h3_unpack_audio_tokens(
rows: torch.Tensor,
*,View on GitHub (pinned to 0132848349)
Solutions
- Pass the same patch_size and channel count that were used when the rows were patchified.
- If rows carry extra features, project/select down to pt*ph*pw*channel dims before unpatchify.
- Persist patch_size/latent_shape alongside the token rows (e.g. in the plan/state dict) so round-trips use matching params.
Example fix
# before latent = minimax_h3_unpatchify_video_tokens(rows, latent_shape=shape, patch_size=(1, 8, 8)) # after latent = minimax_h3_unpatchify_video_tokens(rows, latent_shape=shape, patch_size=(1, 16, 16)) # match patchify
Defensive patterns
Strategy: validation
Validate before calling
pt, ph, pw = patch_size
expected = pt * ph * pw * latent_shape[3]
assert rows.shape[-1] == expected, f"token dim {rows.shape[-1]} != expected {expected}" Type guard
def rows_match_layout(rows, latent_shape, patch_size) -> bool:
pt, ph, pw = patch_size
return rows.ndim == 2 and rows.shape[-1] == pt * ph * pw * latent_shape[-1] Prevention
- Carry patch_size and latent_shape through the pipeline state alongside token rows.
- Never change patch/channel config between patchify and unpatchify without regenerating rows.
When it happens
Trigger: Calling unpatchify with latent_shape=(2,8,8,16) and patch_size=(1,16,16) on rows whose last dim is 1*8*8*16 (produced with patch_size (1,8,8)); or rows carrying an extra projected feature dimension from a DiT output head.
Common situations: Changing patch_size or channel config between patchify and unpatchify calls; feeding raw DiT hidden states instead of the projected token rows; a channel mismatch after switching VAE versions.
Related errors
- video rows {int(rows.shape[0])} must be divisible by t*h*w {
- MiniMax-H3 adaln_t_table must have shape [N, D] with N >= 2,
- {name} must be rank {rank}, got shape={list(tensor.shape)}
- video latent spatial/time dims must be divisible by patch_si
- `dt_bias` must have {HV * K} elements (got {dt_bias.numel()}
AI-assisted analysis of sgl-project/sglang@0132848349 (2026-08-28).
Data as JSON: /api/errors/37fdfb8f349dab61.
Report an issue: GitHub.