Skip to content

Commit 9bd9294

Browse files
jio-HDarkLight1337
andauthored
[Bugfix] Fix MiniCPMV Image input inference failed (#22813)
Signed-off-by: HWH <[email protected]> Signed-off-by: DarkLight1337 <[email protected]> Signed-off-by: Cyrus Leung <[email protected]> Co-authored-by: DarkLight1337 <[email protected]> Co-authored-by: Cyrus Leung <[email protected]>
1 parent da27051 commit 9bd9294

File tree

2 files changed

+60
-27
lines changed

2 files changed

+60
-27
lines changed

vllm/model_executor/models/minicpmv.py

Lines changed: 17 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -85,6 +85,23 @@ class MiniCPMVImagePixelInputs(TensorSchema):
8585
- w: Width
8686
"""
8787

88+
def _validate_nested_tensors(
89+
self,
90+
value: Union[list[torch.Tensor], tuple[torch.Tensor, ...]],
91+
field_name: str,
92+
expected_shape: tuple[Union[int, str], ...],
93+
dynamic_dims: set[str],
94+
) -> tuple[int, ...]:
95+
# value[0] is the scaled image,
96+
# and value[1:] is a collection of image slices.
97+
# It is ensured that all slices in the collection
98+
# have the same shape.
99+
if field_name == "pixel_values":
100+
value = value[1:] if len(value) > 1 else value
101+
102+
return super()._validate_nested_tensors(value, field_name,
103+
expected_shape, dynamic_dims)
104+
88105
type: Literal["pixel_values"] = "pixel_values"
89106

90107
# Note that the image size may vary, so we pass it as a list instead of a

vllm/utils/tensor_schema.py

Lines changed: 43 additions & 27 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,7 @@
11
# SPDX-License-Identifier: Apache-2.0
22
# SPDX-FileCopyrightText: Copyright contributors to the vLLM project
3-
from typing import Annotated, Any, Union, get_args, get_origin, get_type_hints
3+
from typing import (Annotated, Any, Optional, Union, get_args, get_origin,
4+
get_type_hints)
45

56
import torch
67

@@ -11,9 +12,13 @@
1112

1213
class TensorShape:
1314

14-
def __init__(self,
15-
*dims: Union[int, str],
16-
dynamic_dims: set[str, ...] = None) -> None:
15+
def __init__(
16+
self,
17+
*dims: Union[int, str],
18+
dynamic_dims: Optional[set[str]] = None,
19+
) -> None:
20+
super().__init__()
21+
1722
self.dims = dims
1823
self.dynamic_dims = dynamic_dims if dynamic_dims else set()
1924

@@ -44,11 +49,15 @@ def __str__(self) -> str:
4449

4550
class TensorSchema:
4651

47-
def __init__(self,
48-
*,
49-
validate: bool = True,
50-
resolve_bindings: dict[str, int] = None,
51-
**kwargs: Any) -> None:
52+
def __init__(
53+
self,
54+
*,
55+
validate: bool = True,
56+
resolve_bindings: Optional[dict[str, int]] = None,
57+
**kwargs: Any,
58+
) -> None:
59+
super().__init__()
60+
5261
self._resolve_bindings = resolve_bindings if resolve_bindings else {}
5362

5463
for key, value in kwargs.items():
@@ -57,16 +66,19 @@ def __init__(self,
5766
if validate:
5867
self.validate()
5968

60-
def __getitem__(self, item) -> Any:
61-
return getattr(self, item)
69+
def __getitem__(self, key: str) -> Any:
70+
return getattr(self, key)
6271

63-
def get(self, item, default=None) -> Any:
64-
return getattr(self, item, default)
72+
def get(self, key: str, default: Any = None) -> Any:
73+
return getattr(self, key, default)
6574

66-
def _match_shape_with_dynamic(self, actual: tuple[int, ...],
67-
reference: tuple[int, ...],
68-
expected_shape: tuple[Union[int, str], ...],
69-
dynamic_dims: set[str, ...]) -> bool:
75+
def _match_shape_with_dynamic(
76+
self,
77+
actual: tuple[int, ...],
78+
reference: tuple[int, ...],
79+
expected_shape: tuple[Union[int, str], ...],
80+
dynamic_dims: set[str],
81+
) -> bool:
7082
if len(actual) != len(reference) or len(actual) > len(expected_shape):
7183
return False
7284

@@ -84,10 +96,12 @@ def _match_shape_with_dynamic(self, actual: tuple[int, ...],
8496
return True
8597

8698
def _validate_nested_tensors(
87-
self, value: Union[list[torch.Tensor, ...],
88-
tuple[torch.Tensor, ...]], field_name: str,
89-
expected_shape: tuple[Union[int, str], ...],
90-
dynamic_dims: set[str, ...]) -> tuple[int, ...]:
99+
self,
100+
value: Union[list[torch.Tensor], tuple[torch.Tensor, ...]],
101+
field_name: str,
102+
expected_shape: tuple[Union[int, str], ...],
103+
dynamic_dims: set[str],
104+
) -> tuple[int, ...]:
91105
"""Validate a list/tuple of tensors and return the actual shape."""
92106
# Ensure all tensors in the list have the same
93107
# shape, besides dynamic dimensions
@@ -110,12 +124,14 @@ def _validate_nested_tensors(
110124
# shape = (len(list), *tensor.shape)
111125
return (len(value), ) + first.shape
112126

113-
def _validate_tensor_shape_expected(self, actual_shape: tuple[int, ...],
114-
expected_shape: tuple[Union[int, str],
115-
...],
116-
field_name: str, shape_env: dict[str,
117-
int],
118-
dynamic_dims: set[str, ...]) -> None:
127+
def _validate_tensor_shape_expected(
128+
self,
129+
actual_shape: tuple[int, ...],
130+
expected_shape: tuple[Union[int, str], ...],
131+
field_name: str,
132+
shape_env: dict[str, int],
133+
dynamic_dims: set[str],
134+
) -> None:
119135
"""Validate that the actual tensor shape matches the expected shape."""
120136

121137
if len(actual_shape) != len(expected_shape):

0 commit comments

Comments
 (0)