Add support for 2-lane.
Update link-frequency handling to select 750 MHz for 2-lane and 600 MHz for
4-lane, and adjust pixel rate computation accordingly. Extend endpoint
parsing to accept 2 or 4 data lanes.
Signed-off-by: Tarang Raval <tarang.raval@siliconsignals.io>
---
drivers/media/i2c/os05b10.c | 94 ++++++++++++++++++++++++++++---------
1 file changed, 71 insertions(+), 23 deletions(-)
diff --git a/drivers/media/i2c/os05b10.c b/drivers/media/i2c/os05b10.c
index 1393c7b5d860..7107a69157e8 100644
--- a/drivers/media/i2c/os05b10.c
+++ b/drivers/media/i2c/os05b10.c
@@ -114,7 +114,8 @@
#define OS05B10_TRANSPARENT_EFFECT 0xa0
#define OS05B10_ROLLING_BAR_EFFECT 0xc0
-#define OS05B10_LINK_FREQ_600MHZ (600 * HZ_PER_MHZ)
+#define OS05B10_LINK_FREQ_4LANE (600 * HZ_PER_MHZ)
+#define OS05B10_LINK_FREQ_2LANE (750 * HZ_PER_MHZ)
static const struct v4l2_rect os05b10_native_area = {
.top = 0,
@@ -137,12 +138,6 @@ static const char * const os05b10_supply_name[] = {
};
static const struct cci_reg_sequence os05b10_common_regs[] = {
- { OS05B10_REG_PLL_CTRL_01, 0x44 },
- { OS05B10_REG_PLL_CTRL_03, 0x02 },
- { OS05B10_REG_PLL_CTRL_05, 0x32 },
- { OS05B10_REG_PLL_CTRL_06, 0x00 },
- { OS05B10_REG_PLL_CTRL_25, 0x3b },
- { OS05B10_REG_MIPI_SC_CTRL, 0x72 },
{ OS05B10_REG_ANALOG_GAIN_SHORT, 0x0080 },
{ OS05B10_REG_DIGITAL_GAIN_SHORT, 0x0400 },
{ OS05B10_REG_EXPOSURE_SHORT, 0x000020 },
@@ -533,6 +528,24 @@ static const struct cci_reg_sequence mode_1280_720_regs[] = {
{ CCI_REG8(0x4837), 0x0d },
};
+static const struct cci_reg_sequence os05b10_2lane_regs[] = {
+ { OS05B10_REG_PLL_CTRL_01, 0x44 },
+ { OS05B10_REG_PLL_CTRL_03, 0x02 },
+ { OS05B10_REG_PLL_CTRL_05, 0x64 },
+ { OS05B10_REG_PLL_CTRL_06, 0x00 },
+ { OS05B10_REG_PLL_CTRL_25, 0x3b },
+ { OS05B10_REG_MIPI_SC_CTRL, OS05B10_2_LANE_MODE },
+};
+
+static const struct cci_reg_sequence os05b10_4lane_regs[] = {
+ { OS05B10_REG_PLL_CTRL_01, 0x44 },
+ { OS05B10_REG_PLL_CTRL_03, 0x02 },
+ { OS05B10_REG_PLL_CTRL_05, 0x32 },
+ { OS05B10_REG_PLL_CTRL_06, 0x00 },
+ { OS05B10_REG_PLL_CTRL_25, 0x3b },
+ { OS05B10_REG_MIPI_SC_CTRL, OS05B10_4_LANE_MODE },
+};
+
struct os05b10 {
struct device *dev;
struct regmap *cci;
@@ -652,8 +665,12 @@ static const struct os05b10_mode supported_modes_10bit[] = {
},
};
-static const s64 link_frequencies[] = {
- OS05B10_LINK_FREQ_600MHZ,
+static const s64 link_frequencies_4lane[] = {
+ OS05B10_LINK_FREQ_4LANE,
+};
+
+static const s64 link_frequencies_2lane[] = {
+ OS05B10_LINK_FREQ_2LANE,
};
static const u32 os05b10_mbus_codes[] = {
@@ -804,7 +821,9 @@ static int os05b10_enum_mbus_code(struct v4l2_subdev *sd,
static u64 os05b10_pixel_rate(struct os05b10 *os05b10,
const struct os05b10_mode *mode)
{
- u64 link_freq = link_frequencies[os05b10->link_freq_index];
+ u64 link_freq = (os05b10->data_lanes == 2) ?
+ link_frequencies_2lane[os05b10->link_freq_index] :
+ link_frequencies_4lane[os05b10->link_freq_index];
u64 pixel_rate = div_u64(link_freq * 2 * os05b10->data_lanes, mode->bpp);
dev_dbg(os05b10->dev,
@@ -972,6 +991,17 @@ static int os05b10_enable_streams(struct v4l2_subdev *sd,
ret = pm_runtime_resume_and_get(os05b10->dev);
if (ret < 0)
return ret;
+ /* Set pll & mipi lane configuration */
+ if (os05b10->data_lanes == 2)
+ cci_multi_reg_write(os05b10->cci, os05b10_2lane_regs,
+ ARRAY_SIZE(os05b10_2lane_regs), &ret);
+ else
+ cci_multi_reg_write(os05b10->cci, os05b10_4lane_regs,
+ ARRAY_SIZE(os05b10_4lane_regs), &ret);
+ if (ret) {
+ dev_err(os05b10->dev, "failed to write pll & mipi lane registers\n");
+ goto err_rpm_put;
+ }
/* Write common registers */
ret = cci_multi_reg_write(os05b10->cci, os05b10_common_regs,
@@ -1184,22 +1214,39 @@ static int os05b10_parse_endpoint(struct os05b10 *os05b10)
if (ret)
return ret;
- if (bus_cfg.bus.mipi_csi2.num_data_lanes != 4) {
+ if (bus_cfg.bus.mipi_csi2.num_data_lanes != 4 &&
+ bus_cfg.bus.mipi_csi2.num_data_lanes != 2) {
ret = dev_err_probe(os05b10->dev, -EINVAL,
- "only 4 data lanes are supported\n");
+ "4 and 2 data lanes are supported\n");
goto error_out;
}
os05b10->data_lanes = bus_cfg.bus.mipi_csi2.num_data_lanes;
- ret = v4l2_link_freq_to_bitmap(os05b10->dev, bus_cfg.link_frequencies,
- bus_cfg.nr_of_link_frequencies,
- link_frequencies,
- ARRAY_SIZE(link_frequencies),
- &link_freq_bitmap);
- if (ret) {
- dev_err(os05b10->dev, "only 600MHz frequency is available\n");
- goto error_out;
+ if (os05b10->data_lanes == 2) {
+ ret = v4l2_link_freq_to_bitmap(os05b10->dev,
+ bus_cfg.link_frequencies_2lane,
+ bus_cfg.nr_of_link_frequencies_2lane,
+ link_frequencies_2lane,
+ ARRAY_SIZE(link_frequencies_2lane),
+ &link_freq_bitmap);
+ if (ret) {
+ dev_err(os05b10->dev,
+ "For 2 lane 750MHz frequency is available\n");
+ goto error_out;
+ }
+ } else {
+ ret = v4l2_link_freq_to_bitmap(os05b10->dev,
+ bus_cfg.link_frequencies_4lane,
+ bus_cfg.nr_of_link_frequencies_4lane,
+ link_frequencies_4lane,
+ ARRAY_SIZE(link_frequencies_4lane),
+ &link_freq_bitmap);
+ if (ret) {
+ dev_err(os05b10->dev,
+ "For 4 lane 600MHz frequency is available\n");
+ goto error_out;
+ }
}
os05b10->link_freq_index = __ffs(link_freq_bitmap);
@@ -1229,10 +1276,11 @@ static int os05b10_init_controls(struct os05b10 *os05b10)
os05b10->link_freq = v4l2_ctrl_new_int_menu(ctrl_hdlr, &os05b10_ctrl_ops,
V4L2_CID_LINK_FREQ,
- ARRAY_SIZE(link_frequencies) - 1,
+ ARRAY_SIZE(link_frequencies_4lane) - 1,
os05b10->link_freq_index,
- link_frequencies);
-
+ (os05b10->data_lanes == 2) ?
+ link_frequencies_2lane :
+ link_frequencies_4lane);
if (os05b10->link_freq)
os05b10->link_freq->flags |= V4L2_CTRL_FLAG_READ_ONLY;
--
2.34.1
Hi Tarang,
kernel test robot noticed the following build errors:
[auto build test ERROR on sailus-media-tree/master]
[also build test ERROR on linus/master v7.0-rc2 next-20260306]
[cannot apply to sailus-media-tree/streams]
[If your patch is applied to the wrong git tree, kindly drop us a note.
And when submitting patch, we suggest to use '--base' as documented in
https://git-scm.com/docs/git-format-patch#_base_tree_information]
url: https://github.com/intel-lab-lkp/linux/commits/Tarang-Raval/media-i2c-os05b10-drop-unused-group-hold-programming/20260306-212656
base: git://linuxtv.org/sailus/media_tree.git master
patch link: https://lore.kernel.org/r/20260306123304.76722-14-tarang.raval%40siliconsignals.io
patch subject: [PATCH 13/13] media: i2c: os05b10: add 2-lane support
config: openrisc-randconfig-r071-20260307 (https://download.01.org/0day-ci/archive/20260307/202603070920.GtWqPt5Q-lkp@intel.com/config)
compiler: or1k-linux-gcc (GCC) 15.2.0
smatch: v0.5.0-9004-gb810ac53
reproduce (this is a W=1 build): (https://download.01.org/0day-ci/archive/20260307/202603070920.GtWqPt5Q-lkp@intel.com/reproduce)
If you fix the issue in a separate patch/commit (i.e. not just a new version of
the same patch/commit), kindly add following tags
| Reported-by: kernel test robot <lkp@intel.com>
| Closes: https://lore.kernel.org/oe-kbuild-all/202603070920.GtWqPt5Q-lkp@intel.com/
All errors (new ones prefixed by >>):
drivers/media/i2c/os05b10.c: In function 'os05b10_parse_endpoint':
>> drivers/media/i2c/os05b10.c:1228:56: error: 'struct v4l2_fwnode_endpoint' has no member named 'link_frequencies_2lane'; did you mean 'link_frequencies'?
1228 | bus_cfg.link_frequencies_2lane,
| ^~~~~~~~~~~~~~~~~~~~~~
| link_frequencies
>> drivers/media/i2c/os05b10.c:1229:56: error: 'struct v4l2_fwnode_endpoint' has no member named 'nr_of_link_frequencies_2lane'; did you mean 'nr_of_link_frequencies'?
1229 | bus_cfg.nr_of_link_frequencies_2lane,
| ^~~~~~~~~~~~~~~~~~~~~~~~~~~~
| nr_of_link_frequencies
>> drivers/media/i2c/os05b10.c:1240:56: error: 'struct v4l2_fwnode_endpoint' has no member named 'link_frequencies_4lane'; did you mean 'link_frequencies'?
1240 | bus_cfg.link_frequencies_4lane,
| ^~~~~~~~~~~~~~~~~~~~~~
| link_frequencies
>> drivers/media/i2c/os05b10.c:1241:56: error: 'struct v4l2_fwnode_endpoint' has no member named 'nr_of_link_frequencies_4lane'; did you mean 'nr_of_link_frequencies'?
1241 | bus_cfg.nr_of_link_frequencies_4lane,
| ^~~~~~~~~~~~~~~~~~~~~~~~~~~~
| nr_of_link_frequencies
vim +1228 drivers/media/i2c/os05b10.c
1196
1197 static int os05b10_parse_endpoint(struct os05b10 *os05b10)
1198 {
1199 struct v4l2_fwnode_endpoint bus_cfg = {
1200 .bus_type = V4L2_MBUS_CSI2_DPHY
1201 };
1202 unsigned long link_freq_bitmap;
1203 struct fwnode_handle *ep;
1204 int ret;
1205
1206 ep = fwnode_graph_get_endpoint_by_id(dev_fwnode(os05b10->dev), 0, 0, 0);
1207 if (!ep) {
1208 dev_err(os05b10->dev, "Failed to get next endpoint\n");
1209 return -EINVAL;
1210 }
1211
1212 ret = v4l2_fwnode_endpoint_alloc_parse(ep, &bus_cfg);
1213 fwnode_handle_put(ep);
1214 if (ret)
1215 return ret;
1216
1217 if (bus_cfg.bus.mipi_csi2.num_data_lanes != 4 &&
1218 bus_cfg.bus.mipi_csi2.num_data_lanes != 2) {
1219 ret = dev_err_probe(os05b10->dev, -EINVAL,
1220 "4 and 2 data lanes are supported\n");
1221 goto error_out;
1222 }
1223
1224 os05b10->data_lanes = bus_cfg.bus.mipi_csi2.num_data_lanes;
1225
1226 if (os05b10->data_lanes == 2) {
1227 ret = v4l2_link_freq_to_bitmap(os05b10->dev,
> 1228 bus_cfg.link_frequencies_2lane,
> 1229 bus_cfg.nr_of_link_frequencies_2lane,
1230 link_frequencies_2lane,
1231 ARRAY_SIZE(link_frequencies_2lane),
1232 &link_freq_bitmap);
1233 if (ret) {
1234 dev_err(os05b10->dev,
1235 "For 2 lane 750MHz frequency is available\n");
1236 goto error_out;
1237 }
1238 } else {
1239 ret = v4l2_link_freq_to_bitmap(os05b10->dev,
> 1240 bus_cfg.link_frequencies_4lane,
> 1241 bus_cfg.nr_of_link_frequencies_4lane,
1242 link_frequencies_4lane,
1243 ARRAY_SIZE(link_frequencies_4lane),
1244 &link_freq_bitmap);
1245 if (ret) {
1246 dev_err(os05b10->dev,
1247 "For 4 lane 600MHz frequency is available\n");
1248 goto error_out;
1249 }
1250 }
1251
1252 os05b10->link_freq_index = __ffs(link_freq_bitmap);
1253
1254 error_out:
1255 v4l2_fwnode_endpoint_free(&bus_cfg);
1256
1257 return ret;
1258 }
1259
--
0-DAY CI Kernel Test Service
https://github.com/intel/lkp-tests/wiki
© 2016 - 2026 Red Hat, Inc.