diff options
author | Laurent Pinchart <laurent.pinchart@ideasonboard.com> | 2013-11-25 14:19:08 -0500 |
---|---|---|
committer | Mauro Carvalho Chehab <m.chehab@samsung.com> | 2014-05-25 12:04:00 -0400 |
commit | f82f313e9739026ca96342b5b44c5c94072e166a (patch) | |
tree | 135a6deb589d3540298d46aef7665af5f0d9566c /drivers/media/i2c/adv7604.c | |
parent | 5ef54b5955acdcc63ac8ad7cf0aef3d16070773a (diff) |
[media] adv7604: Add DT support
Parse the device tree node to populate platform data. Only the ADV7611
is currently support with DT.
Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
Acked-by: Hans Verkuil <hans.verkuil@cisco.com>
Acked-by: Sylwester Nawrocki <s.nawrocki@samsung.com>
Signed-off-by: Mauro Carvalho Chehab <m.chehab@samsung.com>
Diffstat (limited to 'drivers/media/i2c/adv7604.c')
-rw-r--r-- | drivers/media/i2c/adv7604.c | 80 |
1 files changed, 66 insertions, 14 deletions
diff --git a/drivers/media/i2c/adv7604.c b/drivers/media/i2c/adv7604.c index 342d73d3989b..1323189a45fa 100644 --- a/drivers/media/i2c/adv7604.c +++ b/drivers/media/i2c/adv7604.c | |||
@@ -2663,13 +2663,58 @@ static const struct adv7604_chip_info adv7604_chip_info[] = { | |||
2663 | }, | 2663 | }, |
2664 | }; | 2664 | }; |
2665 | 2665 | ||
2666 | static struct i2c_device_id adv7604_i2c_id[] = { | ||
2667 | { "adv7604", (kernel_ulong_t)&adv7604_chip_info[ADV7604] }, | ||
2668 | { "adv7611", (kernel_ulong_t)&adv7604_chip_info[ADV7611] }, | ||
2669 | { } | ||
2670 | }; | ||
2671 | MODULE_DEVICE_TABLE(i2c, adv7604_i2c_id); | ||
2672 | |||
2673 | static struct of_device_id adv7604_of_id[] __maybe_unused = { | ||
2674 | { .compatible = "adi,adv7611", .data = &adv7604_chip_info[ADV7611] }, | ||
2675 | { } | ||
2676 | }; | ||
2677 | MODULE_DEVICE_TABLE(of, adv7604_of_id); | ||
2678 | |||
2679 | static int adv7604_parse_dt(struct adv7604_state *state) | ||
2680 | { | ||
2681 | /* Disable the interrupt for now as no DT-based board uses it. */ | ||
2682 | state->pdata.int1_config = ADV7604_INT1_CONFIG_DISABLED; | ||
2683 | |||
2684 | /* Use the default I2C addresses. */ | ||
2685 | state->pdata.i2c_addresses[ADV7604_PAGE_AVLINK] = 0x42; | ||
2686 | state->pdata.i2c_addresses[ADV7604_PAGE_CEC] = 0x40; | ||
2687 | state->pdata.i2c_addresses[ADV7604_PAGE_INFOFRAME] = 0x3e; | ||
2688 | state->pdata.i2c_addresses[ADV7604_PAGE_ESDP] = 0x38; | ||
2689 | state->pdata.i2c_addresses[ADV7604_PAGE_DPP] = 0x3c; | ||
2690 | state->pdata.i2c_addresses[ADV7604_PAGE_AFE] = 0x26; | ||
2691 | state->pdata.i2c_addresses[ADV7604_PAGE_REP] = 0x32; | ||
2692 | state->pdata.i2c_addresses[ADV7604_PAGE_EDID] = 0x36; | ||
2693 | state->pdata.i2c_addresses[ADV7604_PAGE_HDMI] = 0x34; | ||
2694 | state->pdata.i2c_addresses[ADV7604_PAGE_TEST] = 0x30; | ||
2695 | state->pdata.i2c_addresses[ADV7604_PAGE_CP] = 0x22; | ||
2696 | state->pdata.i2c_addresses[ADV7604_PAGE_VDP] = 0x24; | ||
2697 | |||
2698 | /* Hardcode the remaining platform data fields. */ | ||
2699 | state->pdata.disable_pwrdnb = 0; | ||
2700 | state->pdata.disable_cable_det_rst = 0; | ||
2701 | state->pdata.default_input = -1; | ||
2702 | state->pdata.blank_data = 1; | ||
2703 | state->pdata.op_656_range = 1; | ||
2704 | state->pdata.alt_data_sat = 1; | ||
2705 | state->pdata.insert_av_codes = 1; | ||
2706 | state->pdata.op_format_mode_sel = ADV7604_OP_FORMAT_MODE0; | ||
2707 | state->pdata.bus_order = ADV7604_BUS_ORDER_RGB; | ||
2708 | |||
2709 | return 0; | ||
2710 | } | ||
2711 | |||
2666 | static int adv7604_probe(struct i2c_client *client, | 2712 | static int adv7604_probe(struct i2c_client *client, |
2667 | const struct i2c_device_id *id) | 2713 | const struct i2c_device_id *id) |
2668 | { | 2714 | { |
2669 | static const struct v4l2_dv_timings cea640x480 = | 2715 | static const struct v4l2_dv_timings cea640x480 = |
2670 | V4L2_DV_BT_CEA_640X480P59_94; | 2716 | V4L2_DV_BT_CEA_640X480P59_94; |
2671 | struct adv7604_state *state; | 2717 | struct adv7604_state *state; |
2672 | struct adv7604_platform_data *pdata = client->dev.platform_data; | ||
2673 | struct v4l2_ctrl_handler *hdl; | 2718 | struct v4l2_ctrl_handler *hdl; |
2674 | struct v4l2_subdev *sd; | 2719 | struct v4l2_subdev *sd; |
2675 | unsigned int i; | 2720 | unsigned int i; |
@@ -2688,19 +2733,32 @@ static int adv7604_probe(struct i2c_client *client, | |||
2688 | return -ENOMEM; | 2733 | return -ENOMEM; |
2689 | } | 2734 | } |
2690 | 2735 | ||
2691 | state->info = &adv7604_chip_info[id->driver_data]; | ||
2692 | state->i2c_clients[ADV7604_PAGE_IO] = client; | 2736 | state->i2c_clients[ADV7604_PAGE_IO] = client; |
2693 | 2737 | ||
2694 | /* initialize variables */ | 2738 | /* initialize variables */ |
2695 | state->restart_stdi_once = true; | 2739 | state->restart_stdi_once = true; |
2696 | state->selected_input = ~0; | 2740 | state->selected_input = ~0; |
2697 | 2741 | ||
2698 | /* platform data */ | 2742 | if (IS_ENABLED(CONFIG_OF) && client->dev.of_node) { |
2699 | if (!pdata) { | 2743 | const struct of_device_id *oid; |
2744 | |||
2745 | oid = of_match_node(adv7604_of_id, client->dev.of_node); | ||
2746 | state->info = oid->data; | ||
2747 | |||
2748 | err = adv7604_parse_dt(state); | ||
2749 | if (err < 0) { | ||
2750 | v4l_err(client, "DT parsing error\n"); | ||
2751 | return err; | ||
2752 | } | ||
2753 | } else if (client->dev.platform_data) { | ||
2754 | struct adv7604_platform_data *pdata = client->dev.platform_data; | ||
2755 | |||
2756 | state->info = (const struct adv7604_chip_info *)id->driver_data; | ||
2757 | state->pdata = *pdata; | ||
2758 | } else { | ||
2700 | v4l_err(client, "No platform data!\n"); | 2759 | v4l_err(client, "No platform data!\n"); |
2701 | return -ENODEV; | 2760 | return -ENODEV; |
2702 | } | 2761 | } |
2703 | state->pdata = *pdata; | ||
2704 | 2762 | ||
2705 | /* Request GPIOs. */ | 2763 | /* Request GPIOs. */ |
2706 | for (i = 0; i < state->info->num_dv_ports; ++i) { | 2764 | for (i = 0; i < state->info->num_dv_ports; ++i) { |
@@ -2799,7 +2857,7 @@ static int adv7604_probe(struct i2c_client *client, | |||
2799 | continue; | 2857 | continue; |
2800 | 2858 | ||
2801 | state->i2c_clients[i] = | 2859 | state->i2c_clients[i] = |
2802 | adv7604_dummy_client(sd, pdata->i2c_addresses[i], | 2860 | adv7604_dummy_client(sd, state->pdata.i2c_addresses[i], |
2803 | 0xf2 + i); | 2861 | 0xf2 + i); |
2804 | if (state->i2c_clients[i] == NULL) { | 2862 | if (state->i2c_clients[i] == NULL) { |
2805 | err = -ENOMEM; | 2863 | err = -ENOMEM; |
@@ -2873,21 +2931,15 @@ static int adv7604_remove(struct i2c_client *client) | |||
2873 | 2931 | ||
2874 | /* ----------------------------------------------------------------------- */ | 2932 | /* ----------------------------------------------------------------------- */ |
2875 | 2933 | ||
2876 | static struct i2c_device_id adv7604_id[] = { | ||
2877 | { "adv7604", ADV7604 }, | ||
2878 | { "adv7611", ADV7611 }, | ||
2879 | { } | ||
2880 | }; | ||
2881 | MODULE_DEVICE_TABLE(i2c, adv7604_id); | ||
2882 | |||
2883 | static struct i2c_driver adv7604_driver = { | 2934 | static struct i2c_driver adv7604_driver = { |
2884 | .driver = { | 2935 | .driver = { |
2885 | .owner = THIS_MODULE, | 2936 | .owner = THIS_MODULE, |
2886 | .name = "adv7604", | 2937 | .name = "adv7604", |
2938 | .of_match_table = of_match_ptr(adv7604_of_id), | ||
2887 | }, | 2939 | }, |
2888 | .probe = adv7604_probe, | 2940 | .probe = adv7604_probe, |
2889 | .remove = adv7604_remove, | 2941 | .remove = adv7604_remove, |
2890 | .id_table = adv7604_id, | 2942 | .id_table = adv7604_i2c_id, |
2891 | }; | 2943 | }; |
2892 | 2944 | ||
2893 | module_i2c_driver(adv7604_driver); | 2945 | module_i2c_driver(adv7604_driver); |