[PATCH v2 1/2] media: uvcvideo: Introduce scattered field for uvc_control_mapping

From: Ricardo Ribalda

Date: Fri Oct 02 2026 - 07:22:07 EST


Most of the mappings are contiguous, but the one for
V4L2_CID_ZOOM_CONTINUOUS is not. Instead it uses bytes 0 and 2 but
not 1.

To force reading the byte 1 every time we set the control we used a
fake size of 0, but that was far from nice.

Instead make a new field for this kind of controls.

Cc: stable@xxxxxxxxxxxxxxx
Fixes: e5225c820c05 ("media: uvcvideo: Send a control event when a Control Change interrupt arrives")
Signed-off-by: Ricardo Ribalda <ribalda@xxxxxxxxxxxx>
---
drivers/media/usb/uvc/uvc_ctrl.c | 6 ++++--
drivers/media/usb/uvc/uvcvideo.h | 6 ++++++
2 files changed, 10 insertions(+), 2 deletions(-)

diff --git a/drivers/media/usb/uvc/uvc_ctrl.c b/drivers/media/usb/uvc/uvc_ctrl.c
index d2f722bc3459..6224ecf28ec6 100644
--- a/drivers/media/usb/uvc/uvc_ctrl.c
+++ b/drivers/media/usb/uvc/uvc_ctrl.c
@@ -998,7 +998,9 @@ static const struct uvc_control_mapping uvc_ctrl_mappings[] = {
.id = V4L2_CID_ZOOM_CONTINUOUS,
.entity = UVC_GUID_UVC_CAMERA,
.selector = UVC_CT_ZOOM_RELATIVE_CONTROL,
- .size = 0,
+ .size = 24,
+ /* Byte 1 (bDigitalZoom) is not part of the mapping. */
+ .scattered = true,
.offset = 0,
.v4l2_type = V4L2_CTRL_TYPE_INTEGER,
.data_type = UVC_CTRL_DATA_TYPE_SIGNED,
@@ -2815,7 +2817,7 @@ int uvc_ctrl_set(struct uvc_fh *handle, struct v4l2_ext_control *xctrl)
* needs to be loaded from the device to perform the read-modify-write
* operation.
*/
- if ((ctrl->info.size * 8) != mapping->size) {
+ if ((ctrl->info.size * 8) != mapping->size || mapping->scattered) {
ret = __uvc_ctrl_load_cur(chain, ctrl);
if (ret < 0)
return ret;
diff --git a/drivers/media/usb/uvc/uvcvideo.h b/drivers/media/usb/uvc/uvcvideo.h
index af8cef94ffff..69ee3d0c971d 100644
--- a/drivers/media/usb/uvc/uvcvideo.h
+++ b/drivers/media/usb/uvc/uvcvideo.h
@@ -126,6 +126,12 @@ struct uvc_control_mapping {
*/
u8 size;

+ /*
+ * True if the mapping does not cover all bits between offset and
+ * offset + size.
+ */
+ bool scattered;
+
u8 offset;
enum v4l2_ctrl_type v4l2_type;
u32 data_type;

--
2.56.0.rc1.315.gc6ed9934b7-goog