[Where problems could occur]

The patch adds an I2C id table and hooks it into the i2c_driver; probe
and runtime PM paths are unchanged. A wrong table entry would bind the
driver to the wrong device or pick the wrong variant data, but the four
entries mirror the driver's existing OF match table. Systems without
one of these VCMs are unaffected.

** Description changed:

  [Impact]
  
  On Intel IPU3 devices whose camera module uses a DW9719 voice-coil focus motor
  (e.g. Microsoft Surface Go 2), no cameras work at all on the 7.0 kernel.
  libcamera enumerates zero cameras, so no application can use the webcam.
  
  This is a regression. Kernels up to and including 6.14 are unaffected, and the
  fix is already in mainline.
  
  [Test Case]
  
  On a Surface Go 2 running Zorin OS 18.1 (Ubuntu 24.04 base),
  kernel 7.0.0-28-generic:
  
-   $ cam -l
-   [0:17:42.116034117] [7128] INFO Camera camera_manager.cpp:284 libcamera 
v0.2.0
-   Available cameras:
-   $
+   $ cam -l
+   [0:17:42.116034117] [7128] INFO Camera camera_manager.cpp:284 libcamera 
v0.2.0
+   Available cameras:
+   $
  
  No cameras, despite all three sensors probing successfully:
  
-   $ dmesg | grep ipu3-cio2
-   ipu3-cio2 0000:00:14.3: Found supported sensor INT33BE:00
-   ipu3-cio2 0000:00:14.3: Found supported sensor INT347A:00
-   ipu3-cio2 0000:00:14.3: Found supported sensor INT347E:00
-   ipu3-cio2 0000:00:14.3: Connected 3 cameras
+   $ dmesg | grep ipu3-cio2
+   ipu3-cio2 0000:00:14.3: Found supported sensor INT33BE:00
+   ipu3-cio2 0000:00:14.3: Found supported sensor INT347A:00
+   ipu3-cio2 0000:00:14.3: Found supported sensor INT347E:00
+   ipu3-cio2 0000:00:14.3: Connected 3 cameras
  
  The focus motor is unbound:
  
-   $ cat /sys/bus/i2c/devices/i2c-INT347A:00-VCM/name
-   dw9719
-   $ cat /sys/bus/i2c/devices/i2c-INT347A:00-VCM/modalias
-   i2c:dw9719
-   $ ls /sys/bus/i2c/devices/i2c-INT347A:00-VCM/driver
-   ls: cannot access '...': No such file or directory
+   $ cat /sys/bus/i2c/devices/i2c-INT347A:00-VCM/name
+   dw9719
+   $ cat /sys/bus/i2c/devices/i2c-INT347A:00-VCM/modalias
+   i2c:dw9719
+   $ ls /sys/bus/i2c/devices/i2c-INT347A:00-VCM/driver
+   ls: cannot access '...': No such file or directory
  
  because dw9719.ko exports no matching alias:
  
-   $ modinfo dw9719 | grep ^alias
-   alias:  of:N*T*Cdongwoon,dw9800kC*
-   alias:  of:N*T*Cdongwoon,dw9800k
-   ...                                  <- OF aliases only, no "i2c:dw9719"
+   $ modinfo dw9719 | grep ^alias
+   alias:  of:N*T*Cdongwoon,dw9800kC*
+   alias:  of:N*T*Cdongwoon,dw9800k
+   ...                                  <- OF aliases only, no "i2c:dw9719"
  
  Consequently the media graph is never completed:
  
-   $ media-ctl -d /dev/media1 -p
-   - entity  1: ipu3-csi2 0 (2 pads, 1 link, 0 routes)    <- no device node
-   - entity 37: ov8865 2-0010 (1 pad, 0 link, 0 routes)   <- zero links
-   - entity 39: ov7251 3-0060 (1 pad, 0 link, 0 routes)
-   - entity 41: ov5693 4-0036 (1 pad, 0 link, 0 routes)
+   $ media-ctl -d /dev/media1 -p
+   - entity  1: ipu3-csi2 0 (2 pads, 1 link, 0 routes)    <- no device node
+   - entity 37: ov8865 2-0010 (1 pad, 0 link, 0 routes)   <- zero links
+   - entity 39: ov7251 3-0060 (1 pad, 0 link, 0 routes)
+   - entity 41: ov5693 4-0036 (1 pad, 0 link, 0 routes)
  
  [Regression Details]
  
  Introduced by:
  
-   commit 15faf0fa1472d1da301498a2e33cdaffe84bc4f1
-   "media: i2c: dw9719: Remove unused i2c device id table"
-   Author: Andre Apitzsch <[email protected]>, 2025-09-20
+   commit 15faf0fa1472d1da301498a2e33cdaffe84bc4f1
+   "media: i2c: dw9719: Remove unused i2c device id table"
+   Author: Andre Apitzsch <[email protected]>, 2025-09-20
  
  which removed dw9719_id_table and the .id_table pointer as part of the rework
  adding DW9718S/DW9761/DW9800K support and switching the driver to OF matching.
  
  The table was not unused. ipu_bridge instantiates these VCMs as plain I2C
  clients with no OF node and no ACPI "compatible" property, so an 
of_match_table
  can never match them; the i2c device ID table was the only thing that ever 
did.
  With it gone, udev's "modprobe i2c:dw9719" matches nothing, the module is 
never
  loaded, and even a manual bind fails with -ENODEV because i2c_device_match()
  has nothing to match on.
  
  Fixed upstream by:
  
-   commit d7fe0d53b2a8b08f6042cc89315118dee49e072e
-   "media: dw9719: Add back the I2C device id table"
-   Author: Sakari Ailus <[email protected]>, 2026-03-26
+   commit d7fe0d53b2a8b08f6042cc89315118dee49e072e
+   "media: dw9719: Add back the I2C device id table"
+   Author: Sakari Ailus <[email protected]>, 2026-03-26
  
  [Why an unbound focus motor disables the whole camera stack]
  
  This is why the symptom looks unrelated to the cause.
  
  ipu_bridge gives the sensor a "lens-focus" fwnode property referencing the 
VCM.
  v4l2_async_register_subdev_sensor() parses that property and registers a
  sub-notifier on the sensor, waiting for the VCM subdev. 
v4l2_async_nf_can_complete()
  recurses into sub-notifiers, so one pending child blocks its parent:
  
-     dw9719 never autoloads (no i2c:dw9719 alias)
-       -> VCM i2c client never binds
-         -> ov8865's lens-focus sub-notifier never completes
-           -> ipu3-cio2's root notifier can never complete
-             -> cio2_notifier_complete() never runs
-               -> no sensor->CSI-2 links, no CSI-2 subdev nodes
-                 -> libcamera finds no usable sensor: zero cameras
+     dw9719 never autoloads (no i2c:dw9719 alias)
+       -> VCM i2c client never binds
+         -> ov8865's lens-focus sub-notifier never completes
+           -> ipu3-cio2's root notifier can never complete
+             -> cio2_notifier_complete() never runs
+               -> no sensor->CSI-2 links, no CSI-2 subdev nodes
+                 -> libcamera finds no usable sensor: zero cameras
  
  So an unbound autofocus motor takes out every camera on the machine, including
  the front webcam, which has no VCM of its own.
  
  [Fix]
  
  Cherry-pick d7fe0d53b2a8 into the 7.0 kernel. It is a self-contained addition
  of the id_table and MODULE_DEVICE_TABLE(i2c, ...), with no dependencies.
  
  [Verification]
  
  Building the fixed upstream dw9719.c as a DKMS module on the affected system
  resolves it completely: the VCM binds, the notifier completes, media links
  appear, and libcamera enumerates both cameras. Reverting reproduces the 
failure.
  
  Working reproducer, diagnostics and full analysis:
  https://github.com/JackInSightsV2/Surface-Go-2---Camera-Fix-for-Zorin-18.1
  
+ [Where problems could occur]
+ 
+ The patch adds an I2C id table and hooks it into the i2c_driver; probe
+ and runtime PM paths are unchanged. A wrong table entry would bind the
+ driver to the wrong device or pick the wrong variant data, but the four
+ entries mirror the driver's existing OF match table. Systems without
+ one of these VCMs are unaffected.
+ 
  [Other Info]
  
  Not Surface-specific: any IPU3 device with an ACPI-enumerated DW9719 (or
  DW9718S/DW9761/DW9800K, all in the same table) is affected on 7.0.
  
  Reported against Zorin OS 18.1, which uses the Ubuntu 24.04 archive and the
  same 7.0.0-28-generic kernel package. Reproducible on stock Ubuntu with the
  same kernel and hardware.

-- 
You received this bug notification because you are a member of Ubuntu
Bugs, which is subscribed to Ubuntu.
https://bugs.launchpad.net/bugs/2162045

Title:
  linux 7.0: dw9719 VCM never binds, disabling all IPU3 cameras
  (regression, fixed upstream)

To manage notifications about this bug go to:
https://bugs.launchpad.net/ubuntu/+source/linux/+bug/2162045/+subscriptions


-- 
ubuntu-bugs mailing list
[email protected]
https://lists.ubuntu.com/mailman/listinfo/ubuntu-bugs

Reply via email to