[PATCH 04/15] media: adv7604: chip info and formats for ADV7612
Add support for the ADV7612 chip as implemented on Renesas' Lager board to adv7604.c, including lists for formats/colourspace/timing selection and an IRQ handler. Signed-off-by: William Towle --- drivers/media/i2c/adv7604.c | 102 +-- 1 file changed, 98 insertions(+), 4 deletions(-) diff --git a/drivers/media/i2c/adv7604.c b/drivers/media/i2c/adv7604.c index 808360f..ebeddd5 100644 --- a/drivers/media/i2c/adv7604.c +++ b/drivers/media/i2c/adv7604.c @@ -81,6 +81,7 @@ MODULE_LICENSE("GPL"); enum adv76xx_type { ADV7604, ADV7611, + ADV7612, }; struct adv76xx_reg_seq { @@ -766,6 +767,23 @@ static const struct adv76xx_format_info adv7611_formats[] = { ADV76XX_OP_MODE_SEL_SDR_422_2X | ADV76XX_OP_FORMAT_SEL_12BIT }, }; +static const struct adv76xx_format_info adv7612_formats[] = { + { MEDIA_BUS_FMT_RGB888_1X24, ADV76XX_OP_CH_SEL_RGB, true, false, + ADV76XX_OP_MODE_SEL_SDR_444 | ADV76XX_OP_FORMAT_SEL_8BIT }, + { MEDIA_BUS_FMT_YUYV8_2X8, ADV76XX_OP_CH_SEL_RGB, false, false, + ADV76XX_OP_MODE_SEL_SDR_422 | ADV76XX_OP_FORMAT_SEL_8BIT }, + { MEDIA_BUS_FMT_YVYU8_2X8, ADV76XX_OP_CH_SEL_RGB, false, true, + ADV76XX_OP_MODE_SEL_SDR_422 | ADV76XX_OP_FORMAT_SEL_8BIT }, + { MEDIA_BUS_FMT_UYVY8_1X16, ADV76XX_OP_CH_SEL_RBG, false, false, + ADV76XX_OP_MODE_SEL_SDR_422_2X | ADV76XX_OP_FORMAT_SEL_8BIT }, + { MEDIA_BUS_FMT_VYUY8_1X16, ADV76XX_OP_CH_SEL_RBG, false, true, + ADV76XX_OP_MODE_SEL_SDR_422_2X | ADV76XX_OP_FORMAT_SEL_8BIT }, + { MEDIA_BUS_FMT_YUYV8_1X16, ADV76XX_OP_CH_SEL_RGB, false, false, + ADV76XX_OP_MODE_SEL_SDR_422_2X | ADV76XX_OP_FORMAT_SEL_8BIT }, + { MEDIA_BUS_FMT_YVYU8_1X16, ADV76XX_OP_CH_SEL_RGB, false, true, + ADV76XX_OP_MODE_SEL_SDR_422_2X | ADV76XX_OP_FORMAT_SEL_8BIT }, +}; + static const struct adv76xx_format_info * adv76xx_format_info(struct adv76xx_state *state, u32 code) { @@ -870,6 +888,16 @@ static unsigned int adv7611_read_cable_det(struct v4l2_subdev *sd) return value & 1; } +static unsigned int adv7612_read_cable_det(struct v4l2_subdev *sd) +{ + /* Reads CABLE_DET_A_RAW. For input B support, need to +* account for bit 7 [MSB] of 0x6a (ie. CABLE_DET_B_RAW) +*/ + u8 value = io_read(sd, 0x6f); + + return value & 1; +} + static int adv76xx_s_detect_tx_5v_ctrl(struct v4l2_subdev *sd) { struct adv76xx_state *state = to_state(sd); @@ -2510,6 +2538,11 @@ static void adv7611_setup_irqs(struct v4l2_subdev *sd) io_write(sd, 0x41, 0xd0); /* STDI irq for any change, disable INT2 */ } +static void adv7612_setup_irqs(struct v4l2_subdev *sd) +{ + io_write(sd, 0x41, 0xd0); /* disable INT2 */ +} + static void adv76xx_unregister_clients(struct adv76xx_state *state) { unsigned int i; @@ -2597,6 +2630,19 @@ static const struct adv76xx_reg_seq adv7611_recommended_settings_hdmi[] = { { ADV76XX_REG_SEQ_TERM, 0 }, }; +static const struct adv76xx_reg_seq adv7612_recommended_settings_hdmi[] = { + { ADV76XX_REG(ADV76XX_PAGE_CP, 0x6c), 0x00 }, + { ADV76XX_REG(ADV76XX_PAGE_HDMI, 0x9b), 0x03 }, + { ADV76XX_REG(ADV76XX_PAGE_HDMI, 0x6f), 0x08 }, + { ADV76XX_REG(ADV76XX_PAGE_HDMI, 0x85), 0x1f }, + { ADV76XX_REG(ADV76XX_PAGE_HDMI, 0x87), 0x70 }, + { ADV76XX_REG(ADV76XX_PAGE_HDMI, 0x57), 0xda }, + { ADV76XX_REG(ADV76XX_PAGE_HDMI, 0x58), 0x01 }, + { ADV76XX_REG(ADV76XX_PAGE_HDMI, 0x03), 0x98 }, + { ADV76XX_REG(ADV76XX_PAGE_HDMI, 0x4c), 0x44 }, + { ADV76XX_REG_SEQ_TERM, 0 }, +}; + static const struct adv76xx_chip_info adv76xx_chip_info[] = { [ADV7604] = { .type = ADV7604, @@ -2685,17 +2731,60 @@ static const struct adv76xx_chip_info adv76xx_chip_info[] = { .field1_vsync_mask = 0x3fff, .field1_vbackporch_mask = 0x3fff, }, + [ADV7612] = { + .type = ADV7612, + .has_afe = false, + .max_port = ADV76XX_PAD_HDMI_PORT_A,/* B not supported */ + .num_dv_ports = 1, /* normally 2 */ + .edid_enable_reg = 0x74, + .edid_status_reg = 0x76, + .lcf_reg = 0xa3, + .tdms_lock_mask = 0x43, + .cable_det_mask = 0x01, + .fmt_change_digital_mask = 0x03, + .cp_csc = 0xf4, + .formats = adv7612_formats, + .nformats = ARRAY_SIZE(adv7612_formats), + .set_termination = adv7611_set_termination, + .setup_irqs = adv7612_setup_irqs, + .read_hdmi_pixelclock = adv7611_read_hdmi_pixelclock, + .read_cable_det = adv7612_read_cable_det, + .recommended_settings = { + [1] = adv7612_recommended_settings_hdmi, + }, + .num_recommended_settings = { +
Re: [PATCH 04/15] media: adv7604: chip info and formats for ADV7612
Hi William, Two comments, see below. On 06/03/2015 03:59 PM, William Towle wrote: > Add support for the ADV7612 chip as implemented on Renesas' Lager > board to adv7604.c, including lists for formats/colourspace/timing > selection and an IRQ handler. > > Signed-off-by: William Towle > --- > drivers/media/i2c/adv7604.c | 91 > +-- > 1 file changed, 87 insertions(+), 4 deletions(-) > > diff --git a/drivers/media/i2c/adv7604.c b/drivers/media/i2c/adv7604.c > index aaa37b0..16646517 100644 > --- a/drivers/media/i2c/adv7604.c > +++ b/drivers/media/i2c/adv7604.c > @@ -80,6 +80,7 @@ MODULE_LICENSE("GPL"); > enum adv76xx_type { > ADV7604, > ADV7611, > + ADV7612, > }; > > struct adv76xx_reg_seq { > @@ -758,6 +759,23 @@ static const struct adv76xx_format_info > adv7611_formats[] = { > ADV76XX_OP_MODE_SEL_SDR_422_2X | ADV76XX_OP_FORMAT_SEL_12BIT }, > }; > > +static const struct adv76xx_format_info adv7612_formats[] = { > + { MEDIA_BUS_FMT_RGB888_1X24, ADV76XX_OP_CH_SEL_RGB, true, false, > + ADV76XX_OP_MODE_SEL_SDR_444 | ADV76XX_OP_FORMAT_SEL_8BIT }, > + { MEDIA_BUS_FMT_YUYV8_2X8, ADV76XX_OP_CH_SEL_RGB, false, false, > + ADV76XX_OP_MODE_SEL_SDR_422 | ADV76XX_OP_FORMAT_SEL_8BIT }, > + { MEDIA_BUS_FMT_YVYU8_2X8, ADV76XX_OP_CH_SEL_RGB, false, true, > + ADV76XX_OP_MODE_SEL_SDR_422 | ADV76XX_OP_FORMAT_SEL_8BIT }, > + { MEDIA_BUS_FMT_UYVY8_1X16, ADV76XX_OP_CH_SEL_RBG, false, false, > + ADV76XX_OP_MODE_SEL_SDR_422_2X | ADV76XX_OP_FORMAT_SEL_8BIT }, > + { MEDIA_BUS_FMT_VYUY8_1X16, ADV76XX_OP_CH_SEL_RBG, false, true, > + ADV76XX_OP_MODE_SEL_SDR_422_2X | ADV76XX_OP_FORMAT_SEL_8BIT }, > + { MEDIA_BUS_FMT_YUYV8_1X16, ADV76XX_OP_CH_SEL_RGB, false, false, > + ADV76XX_OP_MODE_SEL_SDR_422_2X | ADV76XX_OP_FORMAT_SEL_8BIT }, > + { MEDIA_BUS_FMT_YVYU8_1X16, ADV76XX_OP_CH_SEL_RGB, false, true, > + ADV76XX_OP_MODE_SEL_SDR_422_2X | ADV76XX_OP_FORMAT_SEL_8BIT }, > +}; > + > static const struct adv76xx_format_info * > adv76xx_format_info(struct adv76xx_state *state, u32 code) > { > @@ -2471,6 +2489,11 @@ static void adv7611_setup_irqs(struct v4l2_subdev *sd) > io_write(sd, 0x41, 0xd0); /* STDI irq for any change, disable INT2 */ > } > > +static void adv7612_setup_irqs(struct v4l2_subdev *sd) > +{ > + io_write(sd, 0x41, 0xd0); /* disable INT2 */ > +} > + > static void adv76xx_unregister_clients(struct adv76xx_state *state) > { > unsigned int i; > @@ -2558,6 +2581,19 @@ static const struct adv76xx_reg_seq > adv7611_recommended_settings_hdmi[] = { > { ADV76XX_REG_SEQ_TERM, 0 }, > }; > > +static const struct adv76xx_reg_seq adv7612_recommended_settings_hdmi[] = { > + { ADV76XX_REG(ADV76XX_PAGE_CP, 0x6c), 0x00 }, > + { ADV76XX_REG(ADV76XX_PAGE_HDMI, 0x9b), 0x03 }, > + { ADV76XX_REG(ADV76XX_PAGE_HDMI, 0x6f), 0x08 }, > + { ADV76XX_REG(ADV76XX_PAGE_HDMI, 0x85), 0x1f }, > + { ADV76XX_REG(ADV76XX_PAGE_HDMI, 0x87), 0x70 }, > + { ADV76XX_REG(ADV76XX_PAGE_HDMI, 0x57), 0xda }, > + { ADV76XX_REG(ADV76XX_PAGE_HDMI, 0x58), 0x01 }, > + { ADV76XX_REG(ADV76XX_PAGE_HDMI, 0x03), 0x98 }, > + { ADV76XX_REG(ADV76XX_PAGE_HDMI, 0x4c), 0x44 }, > + { ADV76XX_REG_SEQ_TERM, 0 }, > +}; > + > static const struct adv76xx_chip_info adv76xx_chip_info[] = { > [ADV7604] = { > .type = ADV7604, > @@ -2646,17 +2682,59 @@ static const struct adv76xx_chip_info > adv76xx_chip_info[] = { > .field1_vsync_mask = 0x3fff, > .field1_vbackporch_mask = 0x3fff, > }, > + [ADV7612] = { > + .type = ADV7612, > + .has_afe = false, > + .max_port = ADV7604_PAD_HDMI_PORT_B, > + .num_dv_ports = 2, > + .edid_enable_reg = 0x74, > + .edid_status_reg = 0x76, > + .lcf_reg = 0xa3, > + .tdms_lock_mask = 0x43, This looks strange: with two inputs I expect two bits set in the mask, not three. > + .cable_det_mask = 0x01, Same here: I expect to see two bits set, not one. > + .fmt_change_digital_mask = 0x03, > + .formats = adv7612_formats, > + .nformats = ARRAY_SIZE(adv7612_formats), > + .set_termination = adv7611_set_termination, > + .setup_irqs = adv7612_setup_irqs, > + .read_hdmi_pixelclock = adv7611_read_hdmi_pixelclock, > + .read_cable_det = adv7611_read_cable_det, > + .recommended_settings = { > + [1] = adv7612_recommended_settings_hdmi, > + }, > + .num_recommended_settings = { > + [1] = ARRAY_SIZE(adv7612_recommended_settings_hdmi), > + }, > + .page_mask = BIT(ADV76XX_PAGE_IO) | BIT(ADV76XX_PAGE_CEC) | > + BIT(ADV76XX_PAGE_INFOFRAME) | BIT(ADV76XX_PAGE_AFE) | > + BIT(ADV76XX_PAGE_REP) | BIT(ADV76XX_PAGE_
[PATCH 04/15] media: adv7604: chip info and formats for ADV7612
Add support for the ADV7612 chip as implemented on Renesas' Lager board to adv7604.c, including lists for formats/colourspace/timing selection and an IRQ handler. Signed-off-by: William Towle --- drivers/media/i2c/adv7604.c | 91 +-- 1 file changed, 87 insertions(+), 4 deletions(-) diff --git a/drivers/media/i2c/adv7604.c b/drivers/media/i2c/adv7604.c index aaa37b0..16646517 100644 --- a/drivers/media/i2c/adv7604.c +++ b/drivers/media/i2c/adv7604.c @@ -80,6 +80,7 @@ MODULE_LICENSE("GPL"); enum adv76xx_type { ADV7604, ADV7611, + ADV7612, }; struct adv76xx_reg_seq { @@ -758,6 +759,23 @@ static const struct adv76xx_format_info adv7611_formats[] = { ADV76XX_OP_MODE_SEL_SDR_422_2X | ADV76XX_OP_FORMAT_SEL_12BIT }, }; +static const struct adv76xx_format_info adv7612_formats[] = { + { MEDIA_BUS_FMT_RGB888_1X24, ADV76XX_OP_CH_SEL_RGB, true, false, + ADV76XX_OP_MODE_SEL_SDR_444 | ADV76XX_OP_FORMAT_SEL_8BIT }, + { MEDIA_BUS_FMT_YUYV8_2X8, ADV76XX_OP_CH_SEL_RGB, false, false, + ADV76XX_OP_MODE_SEL_SDR_422 | ADV76XX_OP_FORMAT_SEL_8BIT }, + { MEDIA_BUS_FMT_YVYU8_2X8, ADV76XX_OP_CH_SEL_RGB, false, true, + ADV76XX_OP_MODE_SEL_SDR_422 | ADV76XX_OP_FORMAT_SEL_8BIT }, + { MEDIA_BUS_FMT_UYVY8_1X16, ADV76XX_OP_CH_SEL_RBG, false, false, + ADV76XX_OP_MODE_SEL_SDR_422_2X | ADV76XX_OP_FORMAT_SEL_8BIT }, + { MEDIA_BUS_FMT_VYUY8_1X16, ADV76XX_OP_CH_SEL_RBG, false, true, + ADV76XX_OP_MODE_SEL_SDR_422_2X | ADV76XX_OP_FORMAT_SEL_8BIT }, + { MEDIA_BUS_FMT_YUYV8_1X16, ADV76XX_OP_CH_SEL_RGB, false, false, + ADV76XX_OP_MODE_SEL_SDR_422_2X | ADV76XX_OP_FORMAT_SEL_8BIT }, + { MEDIA_BUS_FMT_YVYU8_1X16, ADV76XX_OP_CH_SEL_RGB, false, true, + ADV76XX_OP_MODE_SEL_SDR_422_2X | ADV76XX_OP_FORMAT_SEL_8BIT }, +}; + static const struct adv76xx_format_info * adv76xx_format_info(struct adv76xx_state *state, u32 code) { @@ -2471,6 +2489,11 @@ static void adv7611_setup_irqs(struct v4l2_subdev *sd) io_write(sd, 0x41, 0xd0); /* STDI irq for any change, disable INT2 */ } +static void adv7612_setup_irqs(struct v4l2_subdev *sd) +{ + io_write(sd, 0x41, 0xd0); /* disable INT2 */ +} + static void adv76xx_unregister_clients(struct adv76xx_state *state) { unsigned int i; @@ -2558,6 +2581,19 @@ static const struct adv76xx_reg_seq adv7611_recommended_settings_hdmi[] = { { ADV76XX_REG_SEQ_TERM, 0 }, }; +static const struct adv76xx_reg_seq adv7612_recommended_settings_hdmi[] = { + { ADV76XX_REG(ADV76XX_PAGE_CP, 0x6c), 0x00 }, + { ADV76XX_REG(ADV76XX_PAGE_HDMI, 0x9b), 0x03 }, + { ADV76XX_REG(ADV76XX_PAGE_HDMI, 0x6f), 0x08 }, + { ADV76XX_REG(ADV76XX_PAGE_HDMI, 0x85), 0x1f }, + { ADV76XX_REG(ADV76XX_PAGE_HDMI, 0x87), 0x70 }, + { ADV76XX_REG(ADV76XX_PAGE_HDMI, 0x57), 0xda }, + { ADV76XX_REG(ADV76XX_PAGE_HDMI, 0x58), 0x01 }, + { ADV76XX_REG(ADV76XX_PAGE_HDMI, 0x03), 0x98 }, + { ADV76XX_REG(ADV76XX_PAGE_HDMI, 0x4c), 0x44 }, + { ADV76XX_REG_SEQ_TERM, 0 }, +}; + static const struct adv76xx_chip_info adv76xx_chip_info[] = { [ADV7604] = { .type = ADV7604, @@ -2646,17 +2682,59 @@ static const struct adv76xx_chip_info adv76xx_chip_info[] = { .field1_vsync_mask = 0x3fff, .field1_vbackporch_mask = 0x3fff, }, + [ADV7612] = { + .type = ADV7612, + .has_afe = false, + .max_port = ADV7604_PAD_HDMI_PORT_B, + .num_dv_ports = 2, + .edid_enable_reg = 0x74, + .edid_status_reg = 0x76, + .lcf_reg = 0xa3, + .tdms_lock_mask = 0x43, + .cable_det_mask = 0x01, + .fmt_change_digital_mask = 0x03, + .formats = adv7612_formats, + .nformats = ARRAY_SIZE(adv7612_formats), + .set_termination = adv7611_set_termination, + .setup_irqs = adv7612_setup_irqs, + .read_hdmi_pixelclock = adv7611_read_hdmi_pixelclock, + .read_cable_det = adv7611_read_cable_det, + .recommended_settings = { + [1] = adv7612_recommended_settings_hdmi, + }, + .num_recommended_settings = { + [1] = ARRAY_SIZE(adv7612_recommended_settings_hdmi), + }, + .page_mask = BIT(ADV76XX_PAGE_IO) | BIT(ADV76XX_PAGE_CEC) | + BIT(ADV76XX_PAGE_INFOFRAME) | BIT(ADV76XX_PAGE_AFE) | + BIT(ADV76XX_PAGE_REP) | BIT(ADV76XX_PAGE_EDID) | + BIT(ADV76XX_PAGE_HDMI) | BIT(ADV76XX_PAGE_CP), + .linewidth_mask = 0x1fff, + .field0_height_mask = 0x1fff, + .field1_height_mask = 0x1fff, + .hfrontporch_mask = 0x1fff, + .hsync_mask = 0x1fff, + .hbackp
[PATCH 04/15] media: adv7604: chip info and formats for ADV7612
Add support for the ADV7612 chip as implemented on Renesas' Lager board to adv7604.c, including lists for formats/colourspace/timing selection and an IRQ handler. Signed-off-by: William Towle --- drivers/media/i2c/adv7604.c | 83 +-- 1 file changed, 81 insertions(+), 2 deletions(-) diff --git a/drivers/media/i2c/adv7604.c b/drivers/media/i2c/adv7604.c index aaa37b0..c5a1566 100644 --- a/drivers/media/i2c/adv7604.c +++ b/drivers/media/i2c/adv7604.c @@ -80,6 +80,7 @@ MODULE_LICENSE("GPL"); enum adv76xx_type { ADV7604, ADV7611, + ADV7612, }; struct adv76xx_reg_seq { @@ -758,6 +759,23 @@ static const struct adv76xx_format_info adv7611_formats[] = { ADV76XX_OP_MODE_SEL_SDR_422_2X | ADV76XX_OP_FORMAT_SEL_12BIT }, }; +static const struct adv76xx_format_info adv7612_formats[] = { + { MEDIA_BUS_FMT_RGB888_1X24, ADV76XX_OP_CH_SEL_RGB, true, false, + ADV76XX_OP_MODE_SEL_SDR_444 | ADV76XX_OP_FORMAT_SEL_8BIT }, + { MEDIA_BUS_FMT_YUYV8_2X8, ADV76XX_OP_CH_SEL_RGB, false, false, + ADV76XX_OP_MODE_SEL_SDR_422 | ADV76XX_OP_FORMAT_SEL_8BIT }, + { MEDIA_BUS_FMT_YVYU8_2X8, ADV76XX_OP_CH_SEL_RGB, false, true, + ADV76XX_OP_MODE_SEL_SDR_422 | ADV76XX_OP_FORMAT_SEL_8BIT }, + { MEDIA_BUS_FMT_UYVY8_1X16, ADV76XX_OP_CH_SEL_RBG, false, false, + ADV76XX_OP_MODE_SEL_SDR_422_2X | ADV76XX_OP_FORMAT_SEL_8BIT }, + { MEDIA_BUS_FMT_VYUY8_1X16, ADV76XX_OP_CH_SEL_RBG, false, true, + ADV76XX_OP_MODE_SEL_SDR_422_2X | ADV76XX_OP_FORMAT_SEL_8BIT }, + { MEDIA_BUS_FMT_YUYV8_1X16, ADV76XX_OP_CH_SEL_RGB, false, false, + ADV76XX_OP_MODE_SEL_SDR_422_2X | ADV76XX_OP_FORMAT_SEL_8BIT }, + { MEDIA_BUS_FMT_YVYU8_1X16, ADV76XX_OP_CH_SEL_RGB, false, true, + ADV76XX_OP_MODE_SEL_SDR_422_2X | ADV76XX_OP_FORMAT_SEL_8BIT }, +}; + static const struct adv76xx_format_info * adv76xx_format_info(struct adv76xx_state *state, u32 code) { @@ -2471,6 +2489,11 @@ static void adv7611_setup_irqs(struct v4l2_subdev *sd) io_write(sd, 0x41, 0xd0); /* STDI irq for any change, disable INT2 */ } +static void adv7612_setup_irqs(struct v4l2_subdev *sd) +{ + io_write(sd, 0x41, 0xd0); /* disable INT2 */ +} + static void adv76xx_unregister_clients(struct adv76xx_state *state) { unsigned int i; @@ -2558,6 +2581,19 @@ static const struct adv76xx_reg_seq adv7611_recommended_settings_hdmi[] = { { ADV76XX_REG_SEQ_TERM, 0 }, }; +static const struct adv76xx_reg_seq adv7612_recommended_settings_hdmi[] = { + { ADV76XX_REG(ADV76XX_PAGE_CP, 0x6c), 0x00 }, + { ADV76XX_REG(ADV76XX_PAGE_HDMI, 0x9b), 0x03 }, + { ADV76XX_REG(ADV76XX_PAGE_HDMI, 0x6f), 0x08 }, + { ADV76XX_REG(ADV76XX_PAGE_HDMI, 0x85), 0x1f }, + { ADV76XX_REG(ADV76XX_PAGE_HDMI, 0x87), 0x70 }, + { ADV76XX_REG(ADV76XX_PAGE_HDMI, 0x57), 0xda }, + { ADV76XX_REG(ADV76XX_PAGE_HDMI, 0x58), 0x01 }, + { ADV76XX_REG(ADV76XX_PAGE_HDMI, 0x03), 0x98 }, + { ADV76XX_REG(ADV76XX_PAGE_HDMI, 0x4c), 0x44 }, + { ADV76XX_REG_SEQ_TERM, 0 }, +}; + static const struct adv76xx_chip_info adv76xx_chip_info[] = { [ADV7604] = { .type = ADV7604, @@ -2646,17 +2682,59 @@ static const struct adv76xx_chip_info adv76xx_chip_info[] = { .field1_vsync_mask = 0x3fff, .field1_vbackporch_mask = 0x3fff, }, + [ADV7612] = { + .type = ADV7612, + .has_afe = false, + .max_port = ADV7604_PAD_HDMI_PORT_B, + .num_dv_ports = 2, + .edid_enable_reg = 0x74, + .edid_status_reg = 0x76, + .lcf_reg = 0xa3, + .tdms_lock_mask = 0x43, + .cable_det_mask = 0x01, + .fmt_change_digital_mask = 0x03, + .formats = adv7612_formats, + .nformats = ARRAY_SIZE(adv7612_formats), + .set_termination = adv7611_set_termination, + .setup_irqs = adv7612_setup_irqs, + .read_hdmi_pixelclock = adv7611_read_hdmi_pixelclock, + .read_cable_det = adv7611_read_cable_det, + .recommended_settings = { + [1] = adv7612_recommended_settings_hdmi, + }, + .num_recommended_settings = { + [1] = ARRAY_SIZE(adv7612_recommended_settings_hdmi), + }, + .page_mask = BIT(ADV76XX_PAGE_IO) | BIT(ADV76XX_PAGE_CEC) | + BIT(ADV76XX_PAGE_INFOFRAME) | BIT(ADV76XX_PAGE_AFE) | + BIT(ADV76XX_PAGE_REP) | BIT(ADV76XX_PAGE_EDID) | + BIT(ADV76XX_PAGE_HDMI) | BIT(ADV76XX_PAGE_CP), + .linewidth_mask = 0x1fff, + .field0_height_mask = 0x1fff, + .field1_height_mask = 0x1fff, + .hfrontporch_mask = 0x1fff, + .hsync_mask = 0x1fff, + .hbackpo