On Sun Jul 6 11:53:24 2025 +0200, Hans de Goede wrote: > Add support for the vblank and hblank controls, these controls > are mandatory for using the sensor driver with libcamera. > > Signed-off-by: Hans de Goede <ha...@kernel.org> > Reviewed-by: Andy Shevchenko <a...@kernel.org> > Link: https://lore.kernel.org/r/20250517114106.43494-9-hdego...@redhat.com > Signed-off-by: Mauro Carvalho Chehab <mchehab+hua...@kernel.org>
Patch committed. Thanks, Mauro Carvalho Chehab drivers/staging/media/atomisp/i2c/atomisp-gc0310.c | 38 ++++++++++++++++++++-- 1 file changed, 35 insertions(+), 3 deletions(-) --- diff --git a/drivers/staging/media/atomisp/i2c/atomisp-gc0310.c b/drivers/staging/media/atomisp/i2c/atomisp-gc0310.c index cff1db5390bc..dab736f5d4b3 100644 --- a/drivers/staging/media/atomisp/i2c/atomisp-gc0310.c +++ b/drivers/staging/media/atomisp/i2c/atomisp-gc0310.c @@ -62,9 +62,22 @@ #define GC0310_V_CROP_START_REG CCI_REG16(0x0b) #define GC0310_H_OUTSIZE_REG CCI_REG16(0x0f) #define GC0310_V_OUTSIZE_REG CCI_REG16(0x0d) + #define GC0310_H_BLANKING_REG CCI_REG16(0x05) +/* Hblank-register + sh-delay + H-crop + 4 (from hw) */ +#define GC0310_H_BLANK_DEFAULT (178 + 42 + 4 + 4) + #define GC0310_V_BLANKING_REG CCI_REG16(0x07) +/* Vblank needs an offset compensate for the small V-crop done */ +#define GC0310_V_BLANK_OFFSET 2 +/* Vsync start time + 1 row vsync + vsync end time + offset */ +#define GC0310_V_BLANK_MIN (9 + 1 + 4 + GC0310_V_BLANK_OFFSET) +#define GC0310_V_BLANK_DEFAULT (27 + GC0310_V_BLANK_OFFSET) +#define GC0310_V_BLANK_MAX (4095 - GC0310_NATIVE_HEIGHT) + #define GC0310_SH_DELAY_REG CCI_REG8(0x11) +#define GC0310_VS_START_TIME_REG CCI_REG8(0x12) +#define GC0310_VS_END_TIME_REG CCI_REG8(0x13) #define to_gc0310_sensor(x) container_of(x, struct gc0310_device, sd) @@ -89,6 +102,8 @@ struct gc0310_device { struct v4l2_ctrl *gain; struct v4l2_ctrl *link_freq; struct v4l2_ctrl *pixel_rate; + struct v4l2_ctrl *vblank; + struct v4l2_ctrl *hblank; } ctrls; }; @@ -147,8 +162,7 @@ static const struct reg_sequence gc0310_reset_register[] = { { 0x04, 0xc0 }, /* 0xe8 //58 */ { 0x05, 0x00 }, { 0x06, 0xb2 }, /* 0x0a //HB */ - { 0x07, 0x00 }, - { 0x08, 0x1b }, /* 0x89 //VB */ + /* Vblank (reg 0x07 + 0x08) gets set by the vblank ctrl */ { 0x09, 0x00 }, /* row start */ { 0x0a, 0x00 }, { 0x0b, 0x00 }, /* col start */ @@ -309,6 +323,11 @@ static int gc0310_s_ctrl(struct v4l2_ctrl *ctrl) case V4L2_CID_ANALOGUE_GAIN: ret = gc0310_gain_set(sensor, ctrl->val); break; + case V4L2_CID_VBLANK: + ret = cci_write(sensor->regmap, GC0310_V_BLANKING_REG, + ctrl->val - GC0310_V_BLANK_OFFSET, + NULL); + break; default: ret = -EINVAL; break; @@ -563,7 +582,7 @@ static int gc0310_init_controls(struct gc0310_device *sensor) { struct v4l2_ctrl_handler *hdl = &sensor->ctrls.handler; - v4l2_ctrl_handler_init(hdl, 4); + v4l2_ctrl_handler_init(hdl, 6); /* Use the same lock for controls as for everything else */ hdl->lock = &sensor->input_lock; @@ -583,11 +602,24 @@ static int gc0310_init_controls(struct gc0310_device *sensor) v4l2_ctrl_new_std(hdl, NULL, V4L2_CID_PIXEL_RATE, 0, GC0310_PIXELRATE, 1, GC0310_PIXELRATE); + sensor->ctrls.vblank = + v4l2_ctrl_new_std(hdl, &ctrl_ops, V4L2_CID_VBLANK, + GC0310_V_BLANK_MIN, + GC0310_V_BLANK_MAX, 1, + GC0310_V_BLANK_DEFAULT); + + sensor->ctrls.hblank = + v4l2_ctrl_new_std(hdl, NULL, V4L2_CID_HBLANK, + GC0310_H_BLANK_DEFAULT, + GC0310_H_BLANK_DEFAULT, 1, + GC0310_H_BLANK_DEFAULT); + if (hdl->error) return hdl->error; sensor->ctrls.pixel_rate->flags |= V4L2_CTRL_FLAG_READ_ONLY; sensor->ctrls.link_freq->flags |= V4L2_CTRL_FLAG_READ_ONLY; + sensor->ctrls.hblank->flags |= V4L2_CTRL_FLAG_READ_ONLY; return 0; }