diff options
-rw-r--r-- | drivers/media/i2c/adv7180.c | 56 |
1 files changed, 54 insertions, 2 deletions
diff --git a/drivers/media/i2c/adv7180.c b/drivers/media/i2c/adv7180.c index 84d3b782a2a7..f55364ff2582 100644 --- a/drivers/media/i2c/adv7180.c +++ b/drivers/media/i2c/adv7180.c @@ -158,6 +158,7 @@ struct adv7180_state; #define ADV7180_FLAG_RESET_POWERED BIT(0) +#define ADV7180_FLAG_V2 BIT(1) struct adv7180_chip_info { unsigned int flags; @@ -637,9 +638,18 @@ static int adv7180_select_input(struct adv7180_state *state, unsigned int input) static int adv7182_init(struct adv7180_state *state) { + if (state->chip_info->flags & ADV7180_FLAG_V2) { + /* ADI recommended writes for improved video quality */ + adv7180_write(state, 0x0080, 0x51); + adv7180_write(state, 0x0081, 0x51); + adv7180_write(state, 0x0082, 0x68); + adv7180_write(state, 0x0004, 0x17); + } else { + adv7180_write(state, 0x0004, 0x07); + } + /* ADI required writes */ adv7180_write(state, 0x0003, 0x0c); - adv7180_write(state, 0x0004, 0x07); adv7180_write(state, 0x0013, 0x00); adv7180_write(state, 0x001d, 0x40); @@ -696,6 +706,13 @@ static unsigned int adv7182_lbias_settings[][3] = { [ADV7182_INPUT_TYPE_YPBPR] = { 0x0B, 0x4E, 0xC0 }, }; +static unsigned int adv7280_lbias_settings[][3] = { + [ADV7182_INPUT_TYPE_CVBS] = { 0xCD, 0x4E, 0x80 }, + [ADV7182_INPUT_TYPE_DIFF_CVBS] = { 0xC0, 0x4E, 0x80 }, + [ADV7182_INPUT_TYPE_SVIDEO] = { 0x0B, 0xCE, 0x80 }, + [ADV7182_INPUT_TYPE_YPBPR] = { 0x0B, 0x4E, 0xC0 }, +}; + static int adv7182_select_input(struct adv7180_state *state, unsigned int input) { enum adv7182_input_type input_type; @@ -724,7 +741,10 @@ static int adv7182_select_input(struct adv7180_state *state, unsigned int input) break; } - lbias = adv7182_lbias_settings[input_type]; + if (state->chip_info->flags & ADV7180_FLAG_V2) + lbias = adv7280_lbias_settings[input_type]; + else + lbias = adv7182_lbias_settings[input_type]; for (i = 0; i < ARRAY_SIZE(adv7182_lbias_settings[0]); i++) adv7180_write(state, 0x0052 + i, lbias[i]); @@ -783,6 +803,35 @@ static const struct adv7180_chip_info adv7182_info = { .select_input = adv7182_select_input, }; +static const struct adv7180_chip_info adv7280_info = { + .flags = ADV7180_FLAG_V2, + .valid_input_mask = BIT(ADV7182_INPUT_CVBS_AIN1) | + BIT(ADV7182_INPUT_CVBS_AIN2) | + BIT(ADV7182_INPUT_CVBS_AIN3) | + BIT(ADV7182_INPUT_CVBS_AIN4) | + BIT(ADV7182_INPUT_SVIDEO_AIN1_AIN2) | + BIT(ADV7182_INPUT_SVIDEO_AIN3_AIN4) | + BIT(ADV7182_INPUT_YPRPB_AIN1_AIN2_AIN3), + .init = adv7182_init, + .set_std = adv7182_set_std, + .select_input = adv7182_select_input, +}; + +static const struct adv7180_chip_info adv7281_info = { + .flags = ADV7180_FLAG_V2, + .valid_input_mask = BIT(ADV7182_INPUT_CVBS_AIN1) | + BIT(ADV7182_INPUT_CVBS_AIN2) | + BIT(ADV7182_INPUT_CVBS_AIN7) | + BIT(ADV7182_INPUT_CVBS_AIN8) | + BIT(ADV7182_INPUT_SVIDEO_AIN1_AIN2) | + BIT(ADV7182_INPUT_SVIDEO_AIN7_AIN8) | + BIT(ADV7182_INPUT_DIFF_CVBS_AIN1_AIN2) | + BIT(ADV7182_INPUT_DIFF_CVBS_AIN7_AIN8), + .init = adv7182_init, + .set_std = adv7182_set_std, + .select_input = adv7182_select_input, +}; + static int init_device(struct adv7180_state *state) { int ret; @@ -926,6 +975,9 @@ static int adv7180_remove(struct i2c_client *client) static const struct i2c_device_id adv7180_id[] = { { "adv7180", (kernel_ulong_t)&adv7180_info }, { "adv7182", (kernel_ulong_t)&adv7182_info }, + { "adv7280", (kernel_ulong_t)&adv7280_info }, + { "adv7281", (kernel_ulong_t)&adv7281_info }, + { "adv7282", (kernel_ulong_t)&adv7281_info }, {}, }; MODULE_DEVICE_TABLE(i2c, adv7180_id); |