.. | .. |
---|
| 1 | +// SPDX-License-Identifier: GPL-2.0-only |
---|
1 | 2 | /* |
---|
2 | 3 | * Copyright (C) 2012 Texas Instruments |
---|
3 | 4 | * Author: Rob Clark <robdclark@gmail.com> |
---|
4 | | - * |
---|
5 | | - * This program is free software; you can redistribute it and/or modify it |
---|
6 | | - * under the terms of the GNU General Public License version 2 as published by |
---|
7 | | - * the Free Software Foundation. |
---|
8 | | - * |
---|
9 | | - * This program is distributed in the hope that it will be useful, but WITHOUT |
---|
10 | | - * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or |
---|
11 | | - * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for |
---|
12 | | - * more details. |
---|
13 | | - * |
---|
14 | | - * You should have received a copy of the GNU General Public License along with |
---|
15 | | - * this program. If not, see <http://www.gnu.org/licenses/>. |
---|
16 | 5 | */ |
---|
17 | 6 | |
---|
18 | 7 | #include <linux/component.h> |
---|
.. | .. |
---|
24 | 13 | #include <sound/asoundef.h> |
---|
25 | 14 | #include <sound/hdmi-codec.h> |
---|
26 | 15 | |
---|
27 | | -#include <drm/drmP.h> |
---|
28 | 16 | #include <drm/drm_atomic_helper.h> |
---|
29 | | -#include <drm/drm_crtc_helper.h> |
---|
| 17 | +#include <drm/drm_bridge.h> |
---|
30 | 18 | #include <drm/drm_edid.h> |
---|
31 | 19 | #include <drm/drm_of.h> |
---|
| 20 | +#include <drm/drm_print.h> |
---|
| 21 | +#include <drm/drm_probe_helper.h> |
---|
| 22 | +#include <drm/drm_simple_kms_helper.h> |
---|
32 | 23 | #include <drm/i2c/tda998x.h> |
---|
33 | 24 | |
---|
34 | 25 | #include <media/cec-notifier.h> |
---|
35 | 26 | |
---|
36 | 27 | #define DBG(fmt, ...) DRM_DEBUG(fmt"\n", ##__VA_ARGS__) |
---|
37 | 28 | |
---|
38 | | -struct tda998x_audio_port { |
---|
39 | | - u8 format; /* AFMT_xxx */ |
---|
40 | | - u8 config; /* AP value */ |
---|
| 29 | +enum { |
---|
| 30 | + AUDIO_ROUTE_I2S, |
---|
| 31 | + AUDIO_ROUTE_SPDIF, |
---|
| 32 | + AUDIO_ROUTE_NUM |
---|
| 33 | +}; |
---|
| 34 | + |
---|
| 35 | +struct tda998x_audio_route { |
---|
| 36 | + u8 ena_aclk; |
---|
| 37 | + u8 mux_ap; |
---|
| 38 | + u8 aip_clksel; |
---|
| 39 | +}; |
---|
| 40 | + |
---|
| 41 | +struct tda998x_audio_settings { |
---|
| 42 | + const struct tda998x_audio_route *route; |
---|
| 43 | + struct hdmi_audio_infoframe cea; |
---|
| 44 | + unsigned int sample_rate; |
---|
| 45 | + u8 status[5]; |
---|
| 46 | + u8 ena_ap; |
---|
| 47 | + u8 i2s_format; |
---|
| 48 | + u8 cts_n; |
---|
41 | 49 | }; |
---|
42 | 50 | |
---|
43 | 51 | struct tda998x_priv { |
---|
.. | .. |
---|
50 | 58 | bool is_on; |
---|
51 | 59 | bool supports_infoframes; |
---|
52 | 60 | bool sink_has_audio; |
---|
| 61 | + enum hdmi_quantization_range rgb_quant_range; |
---|
53 | 62 | u8 vip_cntrl_0; |
---|
54 | 63 | u8 vip_cntrl_1; |
---|
55 | 64 | u8 vip_cntrl_2; |
---|
56 | 65 | unsigned long tmds_clock; |
---|
57 | | - struct tda998x_audio_params audio_params; |
---|
| 66 | + struct tda998x_audio_settings audio; |
---|
58 | 67 | |
---|
59 | 68 | struct platform_device *audio_pdev; |
---|
60 | 69 | struct mutex audio_mutex; |
---|
.. | .. |
---|
72 | 81 | struct drm_bridge bridge; |
---|
73 | 82 | struct drm_connector connector; |
---|
74 | 83 | |
---|
75 | | - struct tda998x_audio_port audio_port[2]; |
---|
| 84 | + u8 audio_port_enable[AUDIO_ROUTE_NUM]; |
---|
76 | 85 | struct tda9950_glue cec_glue; |
---|
77 | 86 | struct gpio_desc *calib; |
---|
78 | 87 | struct cec_notifier *cec_notify; |
---|
.. | .. |
---|
241 | 250 | # define HVF_CNTRL_1_PAD(x) (((x) & 3) << 4) |
---|
242 | 251 | # define HVF_CNTRL_1_SEMI_PLANAR (1 << 6) |
---|
243 | 252 | #define REG_RPT_CNTRL REG(0x00, 0xf0) /* write */ |
---|
| 253 | +# define RPT_CNTRL_REPEAT(x) ((x) & 15) |
---|
244 | 254 | #define REG_I2S_FORMAT REG(0x00, 0xfc) /* read/write */ |
---|
245 | | -# define I2S_FORMAT(x) (((x) & 3) << 0) |
---|
| 255 | +# define I2S_FORMAT_PHILIPS (0 << 0) |
---|
| 256 | +# define I2S_FORMAT_LEFT_J (2 << 0) |
---|
| 257 | +# define I2S_FORMAT_RIGHT_J (3 << 0) |
---|
246 | 258 | #define REG_AIP_CLKSEL REG(0x00, 0xfd) /* write */ |
---|
247 | 259 | # define AIP_CLKSEL_AIP_SPDIF (0 << 3) |
---|
248 | 260 | # define AIP_CLKSEL_AIP_I2S (1 << 3) |
---|
.. | .. |
---|
795 | 807 | tda998x_edid_delay_start(priv); |
---|
796 | 808 | } else { |
---|
797 | 809 | schedule_work(&priv->detect_work); |
---|
798 | | - cec_notifier_set_phys_addr(priv->cec_notify, |
---|
799 | | - CEC_PHYS_ADDR_INVALID); |
---|
| 810 | + cec_notifier_phys_addr_invalidate( |
---|
| 811 | + priv->cec_notify); |
---|
800 | 812 | } |
---|
801 | 813 | |
---|
802 | 814 | handled = true; |
---|
.. | .. |
---|
832 | 844 | reg_set(priv, REG_DIP_IF_FLAGS, bit); |
---|
833 | 845 | } |
---|
834 | 846 | |
---|
835 | | -static int tda998x_write_aif(struct tda998x_priv *priv, |
---|
836 | | - struct hdmi_audio_infoframe *cea) |
---|
| 847 | +static void tda998x_write_aif(struct tda998x_priv *priv, |
---|
| 848 | + const struct hdmi_audio_infoframe *cea) |
---|
837 | 849 | { |
---|
838 | 850 | union hdmi_infoframe frame; |
---|
839 | 851 | |
---|
840 | 852 | frame.audio = *cea; |
---|
841 | 853 | |
---|
842 | 854 | tda998x_write_if(priv, DIP_IF_FLAGS_IF4, REG_IF4_HB0, &frame); |
---|
843 | | - |
---|
844 | | - return 0; |
---|
845 | 855 | } |
---|
846 | 856 | |
---|
847 | 857 | static void |
---|
848 | | -tda998x_write_avi(struct tda998x_priv *priv, struct drm_display_mode *mode) |
---|
| 858 | +tda998x_write_avi(struct tda998x_priv *priv, const struct drm_display_mode *mode) |
---|
849 | 859 | { |
---|
850 | 860 | union hdmi_infoframe frame; |
---|
851 | 861 | |
---|
852 | | - drm_hdmi_avi_infoframe_from_display_mode(&frame.avi, mode, false); |
---|
| 862 | + drm_hdmi_avi_infoframe_from_display_mode(&frame.avi, |
---|
| 863 | + &priv->connector, mode); |
---|
853 | 864 | frame.avi.quantization_range = HDMI_QUANTIZATION_RANGE_FULL; |
---|
| 865 | + drm_hdmi_avi_infoframe_quant_range(&frame.avi, &priv->connector, mode, |
---|
| 866 | + priv->rgb_quant_range); |
---|
854 | 867 | |
---|
855 | 868 | tda998x_write_if(priv, DIP_IF_FLAGS_IF2, REG_IF2_HB0, &frame); |
---|
856 | 869 | } |
---|
857 | 870 | |
---|
| 871 | +static void tda998x_write_vsi(struct tda998x_priv *priv, |
---|
| 872 | + const struct drm_display_mode *mode) |
---|
| 873 | +{ |
---|
| 874 | + union hdmi_infoframe frame; |
---|
| 875 | + |
---|
| 876 | + if (drm_hdmi_vendor_infoframe_from_display_mode(&frame.vendor.hdmi, |
---|
| 877 | + &priv->connector, |
---|
| 878 | + mode)) |
---|
| 879 | + reg_clear(priv, REG_DIP_IF_FLAGS, DIP_IF_FLAGS_IF1); |
---|
| 880 | + else |
---|
| 881 | + tda998x_write_if(priv, DIP_IF_FLAGS_IF1, REG_IF1_HB0, &frame); |
---|
| 882 | +} |
---|
| 883 | + |
---|
858 | 884 | /* Audio support */ |
---|
| 885 | + |
---|
| 886 | +static const struct tda998x_audio_route tda998x_audio_route[AUDIO_ROUTE_NUM] = { |
---|
| 887 | + [AUDIO_ROUTE_I2S] = { |
---|
| 888 | + .ena_aclk = 1, |
---|
| 889 | + .mux_ap = MUX_AP_SELECT_I2S, |
---|
| 890 | + .aip_clksel = AIP_CLKSEL_AIP_I2S | AIP_CLKSEL_FS_ACLK, |
---|
| 891 | + }, |
---|
| 892 | + [AUDIO_ROUTE_SPDIF] = { |
---|
| 893 | + .ena_aclk = 0, |
---|
| 894 | + .mux_ap = MUX_AP_SELECT_SPDIF, |
---|
| 895 | + .aip_clksel = AIP_CLKSEL_AIP_SPDIF | AIP_CLKSEL_FS_FS64SPDIF, |
---|
| 896 | + }, |
---|
| 897 | +}; |
---|
| 898 | + |
---|
| 899 | +/* Configure the TDA998x audio data and clock routing. */ |
---|
| 900 | +static int tda998x_derive_routing(struct tda998x_priv *priv, |
---|
| 901 | + struct tda998x_audio_settings *s, |
---|
| 902 | + unsigned int route) |
---|
| 903 | +{ |
---|
| 904 | + s->route = &tda998x_audio_route[route]; |
---|
| 905 | + s->ena_ap = priv->audio_port_enable[route]; |
---|
| 906 | + if (s->ena_ap == 0) { |
---|
| 907 | + dev_err(&priv->hdmi->dev, "no audio configuration found\n"); |
---|
| 908 | + return -EINVAL; |
---|
| 909 | + } |
---|
| 910 | + |
---|
| 911 | + return 0; |
---|
| 912 | +} |
---|
| 913 | + |
---|
| 914 | +/* |
---|
| 915 | + * The audio clock divisor register controls a divider producing Audio_Clk_Out |
---|
| 916 | + * from SERclk by dividing it by 2^n where 0 <= n <= 5. We don't know what |
---|
| 917 | + * Audio_Clk_Out or SERclk are. We guess SERclk is the same as TMDS clock. |
---|
| 918 | + * |
---|
| 919 | + * It seems that Audio_Clk_Out must be the smallest value that is greater |
---|
| 920 | + * than 128*fs, otherwise audio does not function. There is some suggestion |
---|
| 921 | + * that 126*fs is a better value. |
---|
| 922 | + */ |
---|
| 923 | +static u8 tda998x_get_adiv(struct tda998x_priv *priv, unsigned int fs) |
---|
| 924 | +{ |
---|
| 925 | + unsigned long min_audio_clk = fs * 128; |
---|
| 926 | + unsigned long ser_clk = priv->tmds_clock * 1000; |
---|
| 927 | + u8 adiv; |
---|
| 928 | + |
---|
| 929 | + for (adiv = AUDIO_DIV_SERCLK_32; adiv != AUDIO_DIV_SERCLK_1; adiv--) |
---|
| 930 | + if (ser_clk > min_audio_clk << adiv) |
---|
| 931 | + break; |
---|
| 932 | + |
---|
| 933 | + dev_dbg(&priv->hdmi->dev, |
---|
| 934 | + "ser_clk=%luHz fs=%uHz min_aclk=%luHz adiv=%d\n", |
---|
| 935 | + ser_clk, fs, min_audio_clk, adiv); |
---|
| 936 | + |
---|
| 937 | + return adiv; |
---|
| 938 | +} |
---|
| 939 | + |
---|
| 940 | +/* |
---|
| 941 | + * In auto-CTS mode, the TDA998x uses a "measured time stamp" counter to |
---|
| 942 | + * generate the CTS value. It appears that the "measured time stamp" is |
---|
| 943 | + * the number of TDMS clock cycles within a number of audio input clock |
---|
| 944 | + * cycles defined by the k and N parameters defined below, in a similar |
---|
| 945 | + * way to that which is set out in the CTS generation in the HDMI spec. |
---|
| 946 | + * |
---|
| 947 | + * tmdsclk ----> mts -> /m ---> CTS |
---|
| 948 | + * ^ |
---|
| 949 | + * sclk -> /k -> /N |
---|
| 950 | + * |
---|
| 951 | + * CTS = mts / m, where m is 2^M. |
---|
| 952 | + * /k is a divider based on the K value below, K+1 for K < 4, or 8 for K >= 4 |
---|
| 953 | + * /N is a divider based on the HDMI specified N value. |
---|
| 954 | + * |
---|
| 955 | + * This produces the following equation: |
---|
| 956 | + * CTS = tmds_clock * k * N / (sclk * m) |
---|
| 957 | + * |
---|
| 958 | + * When combined with the sink-side equation, and realising that sclk is |
---|
| 959 | + * bclk_ratio * fs, we end up with: |
---|
| 960 | + * k = m * bclk_ratio / 128. |
---|
| 961 | + * |
---|
| 962 | + * Note: S/PDIF always uses a bclk_ratio of 64. |
---|
| 963 | + */ |
---|
| 964 | +static int tda998x_derive_cts_n(struct tda998x_priv *priv, |
---|
| 965 | + struct tda998x_audio_settings *settings, |
---|
| 966 | + unsigned int ratio) |
---|
| 967 | +{ |
---|
| 968 | + switch (ratio) { |
---|
| 969 | + case 16: |
---|
| 970 | + settings->cts_n = CTS_N_M(3) | CTS_N_K(0); |
---|
| 971 | + break; |
---|
| 972 | + case 32: |
---|
| 973 | + settings->cts_n = CTS_N_M(3) | CTS_N_K(1); |
---|
| 974 | + break; |
---|
| 975 | + case 48: |
---|
| 976 | + settings->cts_n = CTS_N_M(3) | CTS_N_K(2); |
---|
| 977 | + break; |
---|
| 978 | + case 64: |
---|
| 979 | + settings->cts_n = CTS_N_M(3) | CTS_N_K(3); |
---|
| 980 | + break; |
---|
| 981 | + case 128: |
---|
| 982 | + settings->cts_n = CTS_N_M(0) | CTS_N_K(0); |
---|
| 983 | + break; |
---|
| 984 | + default: |
---|
| 985 | + dev_err(&priv->hdmi->dev, "unsupported bclk ratio %ufs\n", |
---|
| 986 | + ratio); |
---|
| 987 | + return -EINVAL; |
---|
| 988 | + } |
---|
| 989 | + return 0; |
---|
| 990 | +} |
---|
859 | 991 | |
---|
860 | 992 | static void tda998x_audio_mute(struct tda998x_priv *priv, bool on) |
---|
861 | 993 | { |
---|
.. | .. |
---|
868 | 1000 | } |
---|
869 | 1001 | } |
---|
870 | 1002 | |
---|
871 | | -static int |
---|
872 | | -tda998x_configure_audio(struct tda998x_priv *priv, |
---|
873 | | - struct tda998x_audio_params *params) |
---|
| 1003 | +static void tda998x_configure_audio(struct tda998x_priv *priv) |
---|
874 | 1004 | { |
---|
875 | | - u8 buf[6], clksel_aip, clksel_fs, cts_n, adiv; |
---|
| 1005 | + const struct tda998x_audio_settings *settings = &priv->audio; |
---|
| 1006 | + u8 buf[6], adiv; |
---|
876 | 1007 | u32 n; |
---|
877 | 1008 | |
---|
| 1009 | + /* If audio is not configured, there is nothing to do. */ |
---|
| 1010 | + if (settings->ena_ap == 0) |
---|
| 1011 | + return; |
---|
| 1012 | + |
---|
| 1013 | + adiv = tda998x_get_adiv(priv, settings->sample_rate); |
---|
| 1014 | + |
---|
878 | 1015 | /* Enable audio ports */ |
---|
879 | | - reg_write(priv, REG_ENA_AP, params->config); |
---|
880 | | - |
---|
881 | | - /* Set audio input source */ |
---|
882 | | - switch (params->format) { |
---|
883 | | - case AFMT_SPDIF: |
---|
884 | | - reg_write(priv, REG_ENA_ACLK, 0); |
---|
885 | | - reg_write(priv, REG_MUX_AP, MUX_AP_SELECT_SPDIF); |
---|
886 | | - clksel_aip = AIP_CLKSEL_AIP_SPDIF; |
---|
887 | | - clksel_fs = AIP_CLKSEL_FS_FS64SPDIF; |
---|
888 | | - cts_n = CTS_N_M(3) | CTS_N_K(3); |
---|
889 | | - break; |
---|
890 | | - |
---|
891 | | - case AFMT_I2S: |
---|
892 | | - reg_write(priv, REG_ENA_ACLK, 1); |
---|
893 | | - reg_write(priv, REG_MUX_AP, MUX_AP_SELECT_I2S); |
---|
894 | | - clksel_aip = AIP_CLKSEL_AIP_I2S; |
---|
895 | | - clksel_fs = AIP_CLKSEL_FS_ACLK; |
---|
896 | | - switch (params->sample_width) { |
---|
897 | | - case 16: |
---|
898 | | - cts_n = CTS_N_M(3) | CTS_N_K(1); |
---|
899 | | - break; |
---|
900 | | - case 18: |
---|
901 | | - case 20: |
---|
902 | | - case 24: |
---|
903 | | - cts_n = CTS_N_M(3) | CTS_N_K(2); |
---|
904 | | - break; |
---|
905 | | - default: |
---|
906 | | - case 32: |
---|
907 | | - cts_n = CTS_N_M(3) | CTS_N_K(3); |
---|
908 | | - break; |
---|
909 | | - } |
---|
910 | | - break; |
---|
911 | | - |
---|
912 | | - default: |
---|
913 | | - dev_err(&priv->hdmi->dev, "Unsupported I2S format\n"); |
---|
914 | | - return -EINVAL; |
---|
915 | | - } |
---|
916 | | - |
---|
917 | | - reg_write(priv, REG_AIP_CLKSEL, clksel_aip); |
---|
| 1016 | + reg_write(priv, REG_ENA_AP, settings->ena_ap); |
---|
| 1017 | + reg_write(priv, REG_ENA_ACLK, settings->route->ena_aclk); |
---|
| 1018 | + reg_write(priv, REG_MUX_AP, settings->route->mux_ap); |
---|
| 1019 | + reg_write(priv, REG_I2S_FORMAT, settings->i2s_format); |
---|
| 1020 | + reg_write(priv, REG_AIP_CLKSEL, settings->route->aip_clksel); |
---|
918 | 1021 | reg_clear(priv, REG_AIP_CNTRL_0, AIP_CNTRL_0_LAYOUT | |
---|
919 | 1022 | AIP_CNTRL_0_ACR_MAN); /* auto CTS */ |
---|
920 | | - reg_write(priv, REG_CTS_N, cts_n); |
---|
921 | | - |
---|
922 | | - /* |
---|
923 | | - * Audio input somehow depends on HDMI line rate which is |
---|
924 | | - * related to pixclk. Testing showed that modes with pixclk |
---|
925 | | - * >100MHz need a larger divider while <40MHz need the default. |
---|
926 | | - * There is no detailed info in the datasheet, so we just |
---|
927 | | - * assume 100MHz requires larger divider. |
---|
928 | | - */ |
---|
929 | | - adiv = AUDIO_DIV_SERCLK_8; |
---|
930 | | - if (priv->tmds_clock > 100000) |
---|
931 | | - adiv++; /* AUDIO_DIV_SERCLK_16 */ |
---|
932 | | - |
---|
933 | | - /* S/PDIF asks for a larger divider */ |
---|
934 | | - if (params->format == AFMT_SPDIF) |
---|
935 | | - adiv++; /* AUDIO_DIV_SERCLK_16 or _32 */ |
---|
936 | | - |
---|
| 1023 | + reg_write(priv, REG_CTS_N, settings->cts_n); |
---|
937 | 1024 | reg_write(priv, REG_AUDIO_DIV, adiv); |
---|
938 | 1025 | |
---|
939 | 1026 | /* |
---|
940 | 1027 | * This is the approximate value of N, which happens to be |
---|
941 | 1028 | * the recommended values for non-coherent clocks. |
---|
942 | 1029 | */ |
---|
943 | | - n = 128 * params->sample_rate / 1000; |
---|
| 1030 | + n = 128 * settings->sample_rate / 1000; |
---|
944 | 1031 | |
---|
945 | 1032 | /* Write the CTS and N values */ |
---|
946 | 1033 | buf[0] = 0x44; |
---|
.. | .. |
---|
951 | 1038 | buf[5] = n >> 16; |
---|
952 | 1039 | reg_write_range(priv, REG_ACR_CTS_0, buf, 6); |
---|
953 | 1040 | |
---|
954 | | - /* Set CTS clock reference */ |
---|
955 | | - reg_write(priv, REG_AIP_CLKSEL, clksel_aip | clksel_fs); |
---|
956 | | - |
---|
957 | 1041 | /* Reset CTS generator */ |
---|
958 | 1042 | reg_set(priv, REG_AIP_CNTRL_0, AIP_CNTRL_0_RST_CTS); |
---|
959 | 1043 | reg_clear(priv, REG_AIP_CNTRL_0, AIP_CNTRL_0_RST_CTS); |
---|
.. | .. |
---|
962 | 1046 | * The REG_CH_STAT_B-registers skip IEC958 AES2 byte, because |
---|
963 | 1047 | * there is a separate register for each I2S wire. |
---|
964 | 1048 | */ |
---|
965 | | - buf[0] = params->status[0]; |
---|
966 | | - buf[1] = params->status[1]; |
---|
967 | | - buf[2] = params->status[3]; |
---|
968 | | - buf[3] = params->status[4]; |
---|
| 1049 | + buf[0] = settings->status[0]; |
---|
| 1050 | + buf[1] = settings->status[1]; |
---|
| 1051 | + buf[2] = settings->status[3]; |
---|
| 1052 | + buf[3] = settings->status[4]; |
---|
969 | 1053 | reg_write_range(priv, REG_CH_STAT_B(0), buf, 4); |
---|
970 | 1054 | |
---|
971 | 1055 | tda998x_audio_mute(priv, true); |
---|
972 | 1056 | msleep(20); |
---|
973 | 1057 | tda998x_audio_mute(priv, false); |
---|
974 | 1058 | |
---|
975 | | - return tda998x_write_aif(priv, ¶ms->cea); |
---|
| 1059 | + tda998x_write_aif(priv, &settings->cea); |
---|
976 | 1060 | } |
---|
977 | 1061 | |
---|
978 | 1062 | static int tda998x_audio_hw_params(struct device *dev, void *data, |
---|
.. | .. |
---|
980 | 1064 | struct hdmi_codec_params *params) |
---|
981 | 1065 | { |
---|
982 | 1066 | struct tda998x_priv *priv = dev_get_drvdata(dev); |
---|
983 | | - int i, ret; |
---|
984 | | - struct tda998x_audio_params audio = { |
---|
985 | | - .sample_width = params->sample_width, |
---|
| 1067 | + unsigned int bclk_ratio; |
---|
| 1068 | + bool spdif = daifmt->fmt == HDMI_SPDIF; |
---|
| 1069 | + int ret; |
---|
| 1070 | + struct tda998x_audio_settings audio = { |
---|
986 | 1071 | .sample_rate = params->sample_rate, |
---|
987 | 1072 | .cea = params->cea, |
---|
988 | 1073 | }; |
---|
.. | .. |
---|
992 | 1077 | |
---|
993 | 1078 | switch (daifmt->fmt) { |
---|
994 | 1079 | case HDMI_I2S: |
---|
995 | | - if (daifmt->bit_clk_inv || daifmt->frame_clk_inv || |
---|
996 | | - daifmt->bit_clk_master || daifmt->frame_clk_master) { |
---|
997 | | - dev_err(dev, "%s: Bad flags %d %d %d %d\n", __func__, |
---|
998 | | - daifmt->bit_clk_inv, daifmt->frame_clk_inv, |
---|
999 | | - daifmt->bit_clk_master, |
---|
1000 | | - daifmt->frame_clk_master); |
---|
1001 | | - return -EINVAL; |
---|
1002 | | - } |
---|
1003 | | - for (i = 0; i < ARRAY_SIZE(priv->audio_port); i++) |
---|
1004 | | - if (priv->audio_port[i].format == AFMT_I2S) |
---|
1005 | | - audio.config = priv->audio_port[i].config; |
---|
1006 | | - audio.format = AFMT_I2S; |
---|
| 1080 | + audio.i2s_format = I2S_FORMAT_PHILIPS; |
---|
| 1081 | + break; |
---|
| 1082 | + case HDMI_LEFT_J: |
---|
| 1083 | + audio.i2s_format = I2S_FORMAT_LEFT_J; |
---|
| 1084 | + break; |
---|
| 1085 | + case HDMI_RIGHT_J: |
---|
| 1086 | + audio.i2s_format = I2S_FORMAT_RIGHT_J; |
---|
1007 | 1087 | break; |
---|
1008 | 1088 | case HDMI_SPDIF: |
---|
1009 | | - for (i = 0; i < ARRAY_SIZE(priv->audio_port); i++) |
---|
1010 | | - if (priv->audio_port[i].format == AFMT_SPDIF) |
---|
1011 | | - audio.config = priv->audio_port[i].config; |
---|
1012 | | - audio.format = AFMT_SPDIF; |
---|
| 1089 | + audio.i2s_format = 0; |
---|
1013 | 1090 | break; |
---|
1014 | 1091 | default: |
---|
1015 | 1092 | dev_err(dev, "%s: Invalid format %d\n", __func__, daifmt->fmt); |
---|
1016 | 1093 | return -EINVAL; |
---|
1017 | 1094 | } |
---|
1018 | 1095 | |
---|
1019 | | - if (audio.config == 0) { |
---|
1020 | | - dev_err(dev, "%s: No audio configuration found\n", __func__); |
---|
| 1096 | + if (!spdif && |
---|
| 1097 | + (daifmt->bit_clk_inv || daifmt->frame_clk_inv || |
---|
| 1098 | + daifmt->bit_clk_master || daifmt->frame_clk_master)) { |
---|
| 1099 | + dev_err(dev, "%s: Bad flags %d %d %d %d\n", __func__, |
---|
| 1100 | + daifmt->bit_clk_inv, daifmt->frame_clk_inv, |
---|
| 1101 | + daifmt->bit_clk_master, |
---|
| 1102 | + daifmt->frame_clk_master); |
---|
1021 | 1103 | return -EINVAL; |
---|
1022 | 1104 | } |
---|
1023 | 1105 | |
---|
1024 | | - mutex_lock(&priv->audio_mutex); |
---|
1025 | | - if (priv->supports_infoframes && priv->sink_has_audio) |
---|
1026 | | - ret = tda998x_configure_audio(priv, &audio); |
---|
1027 | | - else |
---|
1028 | | - ret = 0; |
---|
| 1106 | + ret = tda998x_derive_routing(priv, &audio, AUDIO_ROUTE_I2S + spdif); |
---|
| 1107 | + if (ret < 0) |
---|
| 1108 | + return ret; |
---|
1029 | 1109 | |
---|
1030 | | - if (ret == 0) |
---|
1031 | | - priv->audio_params = audio; |
---|
| 1110 | + bclk_ratio = spdif ? 64 : params->sample_width * 2; |
---|
| 1111 | + ret = tda998x_derive_cts_n(priv, &audio, bclk_ratio); |
---|
| 1112 | + if (ret < 0) |
---|
| 1113 | + return ret; |
---|
| 1114 | + |
---|
| 1115 | + mutex_lock(&priv->audio_mutex); |
---|
| 1116 | + priv->audio = audio; |
---|
| 1117 | + if (priv->supports_infoframes && priv->sink_has_audio) |
---|
| 1118 | + tda998x_configure_audio(priv); |
---|
1032 | 1119 | mutex_unlock(&priv->audio_mutex); |
---|
1033 | 1120 | |
---|
1034 | | - return ret; |
---|
| 1121 | + return 0; |
---|
1035 | 1122 | } |
---|
1036 | 1123 | |
---|
1037 | 1124 | static void tda998x_audio_shutdown(struct device *dev, void *data) |
---|
.. | .. |
---|
1041 | 1128 | mutex_lock(&priv->audio_mutex); |
---|
1042 | 1129 | |
---|
1043 | 1130 | reg_write(priv, REG_ENA_AP, 0); |
---|
1044 | | - |
---|
1045 | | - priv->audio_params.format = AFMT_UNUSED; |
---|
| 1131 | + priv->audio.ena_ap = 0; |
---|
1046 | 1132 | |
---|
1047 | 1133 | mutex_unlock(&priv->audio_mutex); |
---|
1048 | 1134 | } |
---|
1049 | 1135 | |
---|
1050 | | -int tda998x_audio_digital_mute(struct device *dev, void *data, bool enable) |
---|
| 1136 | +static int tda998x_audio_mute_stream(struct device *dev, void *data, |
---|
| 1137 | + bool enable, int direction) |
---|
1051 | 1138 | { |
---|
1052 | 1139 | struct tda998x_priv *priv = dev_get_drvdata(dev); |
---|
1053 | 1140 | |
---|
.. | .. |
---|
1075 | 1162 | static const struct hdmi_codec_ops audio_codec_ops = { |
---|
1076 | 1163 | .hw_params = tda998x_audio_hw_params, |
---|
1077 | 1164 | .audio_shutdown = tda998x_audio_shutdown, |
---|
1078 | | - .digital_mute = tda998x_audio_digital_mute, |
---|
| 1165 | + .mute_stream = tda998x_audio_mute_stream, |
---|
1079 | 1166 | .get_eld = tda998x_audio_get_eld, |
---|
| 1167 | + .no_capture_mute = 1, |
---|
1080 | 1168 | }; |
---|
1081 | 1169 | |
---|
1082 | 1170 | static int tda998x_audio_codec_init(struct tda998x_priv *priv, |
---|
.. | .. |
---|
1086 | 1174 | .ops = &audio_codec_ops, |
---|
1087 | 1175 | .max_i2s_channels = 2, |
---|
1088 | 1176 | }; |
---|
1089 | | - int i; |
---|
1090 | 1177 | |
---|
1091 | | - for (i = 0; i < ARRAY_SIZE(priv->audio_port); i++) { |
---|
1092 | | - if (priv->audio_port[i].format == AFMT_I2S && |
---|
1093 | | - priv->audio_port[i].config != 0) |
---|
1094 | | - codec_data.i2s = 1; |
---|
1095 | | - if (priv->audio_port[i].format == AFMT_SPDIF && |
---|
1096 | | - priv->audio_port[i].config != 0) |
---|
1097 | | - codec_data.spdif = 1; |
---|
1098 | | - } |
---|
| 1178 | + if (priv->audio_port_enable[AUDIO_ROUTE_I2S]) |
---|
| 1179 | + codec_data.i2s = 1; |
---|
| 1180 | + if (priv->audio_port_enable[AUDIO_ROUTE_SPDIF]) |
---|
| 1181 | + codec_data.spdif = 1; |
---|
1099 | 1182 | |
---|
1100 | 1183 | priv->audio_pdev = platform_device_register_data( |
---|
1101 | 1184 | dev, HDMI_CODEC_DRV_NAME, PLATFORM_DEVID_AUTO, |
---|
.. | .. |
---|
1122 | 1205 | } |
---|
1123 | 1206 | |
---|
1124 | 1207 | static const struct drm_connector_funcs tda998x_connector_funcs = { |
---|
1125 | | - .dpms = drm_helper_connector_dpms, |
---|
1126 | 1208 | .reset = drm_atomic_helper_connector_reset, |
---|
1127 | 1209 | .fill_modes = drm_helper_probe_single_connector_modes, |
---|
1128 | 1210 | .detect = tda998x_connector_detect, |
---|
.. | .. |
---|
1277 | 1359 | |
---|
1278 | 1360 | /* DRM bridge functions */ |
---|
1279 | 1361 | |
---|
1280 | | -static int tda998x_bridge_attach(struct drm_bridge *bridge) |
---|
| 1362 | +static int tda998x_bridge_attach(struct drm_bridge *bridge, |
---|
| 1363 | + enum drm_bridge_attach_flags flags) |
---|
1281 | 1364 | { |
---|
1282 | 1365 | struct tda998x_priv *priv = bridge_to_tda998x_priv(bridge); |
---|
| 1366 | + |
---|
| 1367 | + if (flags & DRM_BRIDGE_ATTACH_NO_CONNECTOR) { |
---|
| 1368 | + DRM_ERROR("Fix bridge driver to make connector optional!"); |
---|
| 1369 | + return -EINVAL; |
---|
| 1370 | + } |
---|
1283 | 1371 | |
---|
1284 | 1372 | return tda998x_connector_init(priv, bridge->dev); |
---|
1285 | 1373 | } |
---|
.. | .. |
---|
1292 | 1380 | } |
---|
1293 | 1381 | |
---|
1294 | 1382 | static enum drm_mode_status tda998x_bridge_mode_valid(struct drm_bridge *bridge, |
---|
| 1383 | + const struct drm_display_info *info, |
---|
1295 | 1384 | const struct drm_display_mode *mode) |
---|
1296 | 1385 | { |
---|
1297 | 1386 | /* TDA19988 dotclock can go up to 165MHz */ |
---|
.. | .. |
---|
1339 | 1428 | } |
---|
1340 | 1429 | |
---|
1341 | 1430 | static void tda998x_bridge_mode_set(struct drm_bridge *bridge, |
---|
1342 | | - struct drm_display_mode *mode, |
---|
1343 | | - struct drm_display_mode *adjusted_mode) |
---|
| 1431 | + const struct drm_display_mode *mode, |
---|
| 1432 | + const struct drm_display_mode *adjusted_mode) |
---|
1344 | 1433 | { |
---|
1345 | 1434 | struct tda998x_priv *priv = bridge_to_tda998x_priv(bridge); |
---|
1346 | 1435 | unsigned long tmds_clock; |
---|
.. | .. |
---|
1351 | 1440 | u16 vwin1_line_s, vwin1_line_e; |
---|
1352 | 1441 | u16 vwin2_line_s, vwin2_line_e; |
---|
1353 | 1442 | u16 de_pix_s, de_pix_e; |
---|
1354 | | - u8 reg, div, rep; |
---|
| 1443 | + u8 reg, div, rep, sel_clk; |
---|
| 1444 | + |
---|
| 1445 | + /* |
---|
| 1446 | + * Since we are "computer" like, our source invariably produces |
---|
| 1447 | + * full-range RGB. If the monitor supports full-range, then use |
---|
| 1448 | + * it, otherwise reduce to limited-range. |
---|
| 1449 | + */ |
---|
| 1450 | + priv->rgb_quant_range = |
---|
| 1451 | + priv->connector.display_info.rgb_quant_range_selectable ? |
---|
| 1452 | + HDMI_QUANTIZATION_RANGE_FULL : |
---|
| 1453 | + drm_default_rgb_quant_range(adjusted_mode); |
---|
1355 | 1454 | |
---|
1356 | 1455 | /* |
---|
1357 | 1456 | * Internally TDA998x is using ITU-R BT.656 style sync but |
---|
.. | .. |
---|
1414 | 1513 | (mode->vsync_end - mode->vsync_start)/2; |
---|
1415 | 1514 | } |
---|
1416 | 1515 | |
---|
1417 | | - tmds_clock = mode->clock; |
---|
| 1516 | + /* |
---|
| 1517 | + * Select pixel repeat depending on the double-clock flag |
---|
| 1518 | + * (which means we have to repeat each pixel once.) |
---|
| 1519 | + */ |
---|
| 1520 | + rep = mode->flags & DRM_MODE_FLAG_DBLCLK ? 1 : 0; |
---|
| 1521 | + sel_clk = SEL_CLK_ENA_SC_CLK | SEL_CLK_SEL_CLK1 | |
---|
| 1522 | + SEL_CLK_SEL_VRF_CLK(rep ? 2 : 0); |
---|
| 1523 | + |
---|
| 1524 | + /* the TMDS clock is scaled up by the pixel repeat */ |
---|
| 1525 | + tmds_clock = mode->clock * (1 + rep); |
---|
1418 | 1526 | |
---|
1419 | 1527 | /* |
---|
1420 | 1528 | * The divisor is power-of-2. The TDA9983B datasheet gives |
---|
.. | .. |
---|
1429 | 1537 | break; |
---|
1430 | 1538 | |
---|
1431 | 1539 | mutex_lock(&priv->audio_mutex); |
---|
| 1540 | + |
---|
| 1541 | + priv->tmds_clock = tmds_clock; |
---|
1432 | 1542 | |
---|
1433 | 1543 | /* mute the audio FIFO: */ |
---|
1434 | 1544 | reg_set(priv, REG_AIP_CNTRL_0, AIP_CNTRL_0_RST_FIFO); |
---|
.. | .. |
---|
1452 | 1562 | reg_write(priv, REG_SERIALIZER, 0); |
---|
1453 | 1563 | reg_write(priv, REG_HVF_CNTRL_1, HVF_CNTRL_1_VQR(0)); |
---|
1454 | 1564 | |
---|
1455 | | - /* TODO enable pixel repeat for pixel rates less than 25Msamp/s */ |
---|
1456 | | - rep = 0; |
---|
1457 | | - reg_write(priv, REG_RPT_CNTRL, 0); |
---|
1458 | | - reg_write(priv, REG_SEL_CLK, SEL_CLK_SEL_VRF_CLK(0) | |
---|
1459 | | - SEL_CLK_SEL_CLK1 | SEL_CLK_ENA_SC_CLK); |
---|
1460 | | - |
---|
| 1565 | + reg_write(priv, REG_RPT_CNTRL, RPT_CNTRL_REPEAT(rep)); |
---|
| 1566 | + reg_write(priv, REG_SEL_CLK, sel_clk); |
---|
1461 | 1567 | reg_write(priv, REG_PLL_SERIAL_2, PLL_SERIAL_2_SRL_NOSC(div) | |
---|
1462 | 1568 | PLL_SERIAL_2_SRL_PR(rep)); |
---|
1463 | 1569 | |
---|
1464 | | - /* set color matrix bypass flag: */ |
---|
1465 | | - reg_write(priv, REG_MAT_CONTRL, MAT_CONTRL_MAT_BP | |
---|
1466 | | - MAT_CONTRL_MAT_SC(1)); |
---|
1467 | | - reg_set(priv, REG_FEAT_POWERDOWN, FEAT_POWERDOWN_CSC); |
---|
| 1570 | + /* set color matrix according to output rgb quant range */ |
---|
| 1571 | + if (priv->rgb_quant_range == HDMI_QUANTIZATION_RANGE_LIMITED) { |
---|
| 1572 | + static u8 tda998x_full_to_limited_range[] = { |
---|
| 1573 | + MAT_CONTRL_MAT_SC(2), |
---|
| 1574 | + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, |
---|
| 1575 | + 0x03, 0x6f, 0x00, 0x00, 0x00, 0x00, |
---|
| 1576 | + 0x00, 0x00, 0x03, 0x6f, 0x00, 0x00, |
---|
| 1577 | + 0x00, 0x00, 0x00, 0x00, 0x03, 0x6f, |
---|
| 1578 | + 0x00, 0x40, 0x00, 0x40, 0x00, 0x40 |
---|
| 1579 | + }; |
---|
| 1580 | + reg_clear(priv, REG_FEAT_POWERDOWN, FEAT_POWERDOWN_CSC); |
---|
| 1581 | + reg_write_range(priv, REG_MAT_CONTRL, |
---|
| 1582 | + tda998x_full_to_limited_range, |
---|
| 1583 | + sizeof(tda998x_full_to_limited_range)); |
---|
| 1584 | + } else { |
---|
| 1585 | + reg_write(priv, REG_MAT_CONTRL, MAT_CONTRL_MAT_BP | |
---|
| 1586 | + MAT_CONTRL_MAT_SC(1)); |
---|
| 1587 | + reg_set(priv, REG_FEAT_POWERDOWN, FEAT_POWERDOWN_CSC); |
---|
| 1588 | + } |
---|
1468 | 1589 | |
---|
1469 | 1590 | /* set BIAS tmds value: */ |
---|
1470 | 1591 | reg_write(priv, REG_ANA_GENERAL, 0x09); |
---|
.. | .. |
---|
1525 | 1646 | /* must be last register set: */ |
---|
1526 | 1647 | reg_write(priv, REG_TBG_CNTRL_0, 0); |
---|
1527 | 1648 | |
---|
1528 | | - priv->tmds_clock = adjusted_mode->clock; |
---|
1529 | | - |
---|
1530 | 1649 | /* CEA-861B section 6 says that: |
---|
1531 | 1650 | * CEA version 1 (CEA-861) has no support for infoframes. |
---|
1532 | 1651 | * CEA version 2 (CEA-861A) supports version 1 AVI infoframes, |
---|
.. | .. |
---|
1548 | 1667 | reg_set(priv, REG_TX33, TX33_HDMI); |
---|
1549 | 1668 | |
---|
1550 | 1669 | tda998x_write_avi(priv, adjusted_mode); |
---|
| 1670 | + tda998x_write_vsi(priv, adjusted_mode); |
---|
1551 | 1671 | |
---|
1552 | | - if (priv->audio_params.format != AFMT_UNUSED && |
---|
1553 | | - priv->sink_has_audio) |
---|
1554 | | - tda998x_configure_audio(priv, &priv->audio_params); |
---|
| 1672 | + if (priv->sink_has_audio) |
---|
| 1673 | + tda998x_configure_audio(priv); |
---|
1555 | 1674 | } |
---|
1556 | 1675 | |
---|
1557 | 1676 | mutex_unlock(&priv->audio_mutex); |
---|
.. | .. |
---|
1580 | 1699 | return 0; |
---|
1581 | 1700 | |
---|
1582 | 1701 | size /= sizeof(u32); |
---|
1583 | | - if (size > 2 * ARRAY_SIZE(priv->audio_port) || size % 2 != 0) { |
---|
| 1702 | + if (size > 2 * ARRAY_SIZE(priv->audio_port_enable) || size % 2 != 0) { |
---|
1584 | 1703 | dev_err(&priv->hdmi->dev, |
---|
1585 | 1704 | "Bad number of elements in audio-ports dt-property\n"); |
---|
1586 | 1705 | return -EINVAL; |
---|
.. | .. |
---|
1589 | 1708 | size /= 2; |
---|
1590 | 1709 | |
---|
1591 | 1710 | for (i = 0; i < size; i++) { |
---|
| 1711 | + unsigned int route; |
---|
1592 | 1712 | u8 afmt = be32_to_cpup(&port_data[2*i]); |
---|
1593 | 1713 | u8 ena_ap = be32_to_cpup(&port_data[2*i+1]); |
---|
1594 | 1714 | |
---|
1595 | | - if (afmt != AFMT_SPDIF && afmt != AFMT_I2S) { |
---|
| 1715 | + switch (afmt) { |
---|
| 1716 | + case AFMT_I2S: |
---|
| 1717 | + route = AUDIO_ROUTE_I2S; |
---|
| 1718 | + break; |
---|
| 1719 | + case AFMT_SPDIF: |
---|
| 1720 | + route = AUDIO_ROUTE_SPDIF; |
---|
| 1721 | + break; |
---|
| 1722 | + default: |
---|
1596 | 1723 | dev_err(&priv->hdmi->dev, |
---|
1597 | 1724 | "Bad audio format %u\n", afmt); |
---|
1598 | 1725 | return -EINVAL; |
---|
1599 | 1726 | } |
---|
1600 | 1727 | |
---|
1601 | | - priv->audio_port[i].format = afmt; |
---|
1602 | | - priv->audio_port[i].config = ena_ap; |
---|
1603 | | - } |
---|
| 1728 | + if (!ena_ap) { |
---|
| 1729 | + dev_err(&priv->hdmi->dev, "invalid zero port config\n"); |
---|
| 1730 | + continue; |
---|
| 1731 | + } |
---|
1604 | 1732 | |
---|
1605 | | - if (priv->audio_port[0].format == priv->audio_port[1].format) { |
---|
1606 | | - dev_err(&priv->hdmi->dev, |
---|
1607 | | - "There can only be on I2S port and one SPDIF port\n"); |
---|
1608 | | - return -EINVAL; |
---|
| 1733 | + if (priv->audio_port_enable[route]) { |
---|
| 1734 | + dev_err(&priv->hdmi->dev, |
---|
| 1735 | + "%s format already configured\n", |
---|
| 1736 | + route == AUDIO_ROUTE_SPDIF ? "SPDIF" : "I2S"); |
---|
| 1737 | + return -EINVAL; |
---|
| 1738 | + } |
---|
| 1739 | + |
---|
| 1740 | + priv->audio_port_enable[route] = ena_ap; |
---|
1609 | 1741 | } |
---|
1610 | 1742 | return 0; |
---|
1611 | 1743 | } |
---|
1612 | 1744 | |
---|
1613 | | -static void tda998x_set_config(struct tda998x_priv *priv, |
---|
1614 | | - const struct tda998x_encoder_params *p) |
---|
| 1745 | +static int tda998x_set_config(struct tda998x_priv *priv, |
---|
| 1746 | + const struct tda998x_encoder_params *p) |
---|
1615 | 1747 | { |
---|
1616 | 1748 | priv->vip_cntrl_0 = VIP_CNTRL_0_SWAP_A(p->swap_a) | |
---|
1617 | 1749 | (p->mirr_a ? VIP_CNTRL_0_MIRR_A : 0) | |
---|
.. | .. |
---|
1626 | 1758 | VIP_CNTRL_2_SWAP_F(p->swap_f) | |
---|
1627 | 1759 | (p->mirr_f ? VIP_CNTRL_2_MIRR_F : 0); |
---|
1628 | 1760 | |
---|
1629 | | - priv->audio_params = p->audio_params; |
---|
| 1761 | + if (p->audio_params.format != AFMT_UNUSED) { |
---|
| 1762 | + unsigned int ratio, route; |
---|
| 1763 | + bool spdif = p->audio_params.format == AFMT_SPDIF; |
---|
| 1764 | + |
---|
| 1765 | + route = AUDIO_ROUTE_I2S + spdif; |
---|
| 1766 | + |
---|
| 1767 | + priv->audio.route = &tda998x_audio_route[route]; |
---|
| 1768 | + priv->audio.cea = p->audio_params.cea; |
---|
| 1769 | + priv->audio.sample_rate = p->audio_params.sample_rate; |
---|
| 1770 | + memcpy(priv->audio.status, p->audio_params.status, |
---|
| 1771 | + min(sizeof(priv->audio.status), |
---|
| 1772 | + sizeof(p->audio_params.status))); |
---|
| 1773 | + priv->audio.ena_ap = p->audio_params.config; |
---|
| 1774 | + priv->audio.i2s_format = I2S_FORMAT_PHILIPS; |
---|
| 1775 | + |
---|
| 1776 | + ratio = spdif ? 64 : p->audio_params.sample_width * 2; |
---|
| 1777 | + return tda998x_derive_cts_n(priv, &priv->audio, ratio); |
---|
| 1778 | + } |
---|
| 1779 | + |
---|
| 1780 | + return 0; |
---|
1630 | 1781 | } |
---|
1631 | 1782 | |
---|
1632 | 1783 | static void tda998x_destroy(struct device *dev) |
---|
.. | .. |
---|
1650 | 1801 | |
---|
1651 | 1802 | i2c_unregister_device(priv->cec); |
---|
1652 | 1803 | |
---|
1653 | | - if (priv->cec_notify) |
---|
1654 | | - cec_notifier_put(priv->cec_notify); |
---|
| 1804 | + cec_notifier_conn_unregister(priv->cec_notify); |
---|
1655 | 1805 | } |
---|
1656 | 1806 | |
---|
1657 | 1807 | static int tda998x_create(struct device *dev) |
---|
.. | .. |
---|
1776 | 1926 | cec_write(priv, REG_CEC_RXSHPDINTENA, CEC_RXSHPDLEV_HPD); |
---|
1777 | 1927 | } |
---|
1778 | 1928 | |
---|
1779 | | - priv->cec_notify = cec_notifier_get(dev); |
---|
| 1929 | + priv->cec_notify = cec_notifier_conn_register(dev, NULL, NULL); |
---|
1780 | 1930 | if (!priv->cec_notify) { |
---|
1781 | 1931 | ret = -ENOMEM; |
---|
1782 | 1932 | goto fail; |
---|
.. | .. |
---|
1803 | 1953 | cec_info.platform_data = &priv->cec_glue; |
---|
1804 | 1954 | cec_info.irq = client->irq; |
---|
1805 | 1955 | |
---|
1806 | | - priv->cec = i2c_new_device(client->adapter, &cec_info); |
---|
1807 | | - if (!priv->cec) { |
---|
1808 | | - ret = -ENODEV; |
---|
| 1956 | + priv->cec = i2c_new_client_device(client->adapter, &cec_info); |
---|
| 1957 | + if (IS_ERR(priv->cec)) { |
---|
| 1958 | + ret = PTR_ERR(priv->cec); |
---|
1809 | 1959 | goto fail; |
---|
1810 | 1960 | } |
---|
1811 | 1961 | |
---|
.. | .. |
---|
1825 | 1975 | if (ret) |
---|
1826 | 1976 | goto fail; |
---|
1827 | 1977 | |
---|
1828 | | - if (priv->audio_port[0].format != AFMT_UNUSED) |
---|
| 1978 | + if (priv->audio_port_enable[AUDIO_ROUTE_I2S] || |
---|
| 1979 | + priv->audio_port_enable[AUDIO_ROUTE_SPDIF]) |
---|
1829 | 1980 | tda998x_audio_codec_init(priv, &client->dev); |
---|
1830 | 1981 | } else if (dev->platform_data) { |
---|
1831 | | - tda998x_set_config(priv, dev->platform_data); |
---|
| 1982 | + ret = tda998x_set_config(priv, dev->platform_data); |
---|
| 1983 | + if (ret) |
---|
| 1984 | + goto fail; |
---|
1832 | 1985 | } |
---|
1833 | 1986 | |
---|
1834 | 1987 | priv->bridge.funcs = &tda998x_bridge_funcs; |
---|
.. | .. |
---|
1848 | 2001 | |
---|
1849 | 2002 | /* DRM encoder functions */ |
---|
1850 | 2003 | |
---|
1851 | | -static void tda998x_encoder_destroy(struct drm_encoder *encoder) |
---|
1852 | | -{ |
---|
1853 | | - drm_encoder_cleanup(encoder); |
---|
1854 | | -} |
---|
1855 | | - |
---|
1856 | | -static const struct drm_encoder_funcs tda998x_encoder_funcs = { |
---|
1857 | | - .destroy = tda998x_encoder_destroy, |
---|
1858 | | -}; |
---|
1859 | | - |
---|
1860 | 2004 | static int tda998x_encoder_init(struct device *dev, struct drm_device *drm) |
---|
1861 | 2005 | { |
---|
1862 | 2006 | struct tda998x_priv *priv = dev_get_drvdata(dev); |
---|
.. | .. |
---|
1874 | 2018 | |
---|
1875 | 2019 | priv->encoder.possible_crtcs = crtcs; |
---|
1876 | 2020 | |
---|
1877 | | - ret = drm_encoder_init(drm, &priv->encoder, &tda998x_encoder_funcs, |
---|
1878 | | - DRM_MODE_ENCODER_TMDS, NULL); |
---|
| 2021 | + ret = drm_simple_encoder_init(drm, &priv->encoder, |
---|
| 2022 | + DRM_MODE_ENCODER_TMDS); |
---|
1879 | 2023 | if (ret) |
---|
1880 | 2024 | goto err_encoder; |
---|
1881 | 2025 | |
---|
1882 | | - ret = drm_bridge_attach(&priv->encoder, &priv->bridge, NULL); |
---|
| 2026 | + ret = drm_bridge_attach(&priv->encoder, &priv->bridge, NULL, 0); |
---|
1883 | 2027 | if (ret) |
---|
1884 | 2028 | goto err_bridge; |
---|
1885 | 2029 | |
---|