[PATCH] media: i2c: thp7312: bound the focus lookup against the table size

From: Guo Zihao

Date: Fri Sep 18 2026 - 02:32:51 EST


thp7312_set_focus() indexes thp7312_focus_values[] with the value of the
V4L2_CID_FOCUS_ABSOLUTE control:

if (thp7312->focus_absolute->is_new) {
unsigned int value;

value = thp7312_focus_values[thp7312->focus_absolute->val];

The control is registered with the table size as its maximum:

v4l2_ctrl_new_std(hdl, &thp7312_ctrl_ops,
V4L2_CID_FOCUS_ABSOLUTE,
0, ARRAY_SIZE(thp7312_focus_values),
1, 0);

The table has 19 entries, so the valid indices are 0 to 18, but
maximum is an inclusive bound in the control framework. For an integer
control the framework rounds the value into [minimum, maximum] with
ROUND_TO_RANGE() in std_validate_elem() and accepts the bound itself, so
a value of 19 passes. The read one past the end of the array then returns
whatever follows the table in the driver image, and that value is
written to the sensor.

Reject a value that is not a valid index before the lookup. The control
range is the safer place for the bound, but leaving the lookup guarded
keeps the table and its only user consistent with each other; narrowing
the control is a follow-up that does not affect this fix.

No Fixes tag. The table, its registration and the lookup all come from
the initial driver import, 7a52ab415b43 ("media: i2c: Add driver for
THine THP7312"), and have not been touched since.

Reviewed-by: Liu Weibin <liuwb@xxxxxxxxxxxx>
Signed-off-by: Guo Zihao <guozh23@xxxxxxxxxxxx>
---
The value is reachable from userspace through the control API
(VIDIOC_S_CTRL / VIDIOC_S_EXT_CTRLS) on the sensor's V4L2 subdev node, so
any user with access to the device can set it to the maximum.

The read is of a u16 past a static const table, so the usual outcome is
reading an adjacent constant rather than anything sensitive; the value
is then written to the sensor. I am reporting it because the same
off-by-one is easy for the next person to repeat when the table grows.

drivers/media/i2c/thp7312.c | 5 +++++
1 file changed, 5 insertions(+)

diff --git a/drivers/media/i2c/thp7312.c b/drivers/media/i2c/thp7312.c
index 775cfba18..20698b7a1 100644
--- a/drivers/media/i2c/thp7312.c
+++ b/drivers/media/i2c/thp7312.c
@@ -931,6 +931,11 @@ static int thp7312_set_focus(struct thp7312_device *thp7312)
if (thp7312->focus_absolute->is_new) {
unsigned int value;

+ if (thp7312->focus_absolute->val < 0 ||
+ thp7312->focus_absolute->val >=
+ ARRAY_SIZE(thp7312_focus_values))
+ return -EINVAL;
+
value = thp7312_focus_values[thp7312->focus_absolute->val];

ret = cci_write(thp7312->regmap,
--
2.50.1