From 1e75841e39355658327e6e97d58dea4f0507b337 Mon Sep 17 00:00:00 2001 From: Yong Qin Date: Thu, 31 May 2018 19:53:09 +0800 Subject: [PATCH] cec: add transwitch cec config [1/1] PD#165002: cec: for support transwitch cec ip Change-Id: I05ec182bbb1962a3a0b42702f87ff15e9de681b0 Signed-off-by: Yong Qin --- arch/arm64/boot/dts/amlogic/mesong12a.dtsi | 2 +- .../boot/dts/amlogic/txlx_t962e_r321.dts | 11 +- .../boot/dts/amlogic/txlx_t962x_r311_1g.dts | 11 +- .../boot/dts/amlogic/txlx_t962x_r311_2g.dts | 11 +- .../boot/dts/amlogic/txlx_t962x_r311_720p.dts | 11 +- drivers/amlogic/cec/hdmi_ao_cec.c | 190 +++++++++++++----- 6 files changed, 167 insertions(+), 69 deletions(-) diff --git a/arch/arm64/boot/dts/amlogic/mesong12a.dtsi b/arch/arm64/boot/dts/amlogic/mesong12a.dtsi index 6e1ffa502581..a45a59e2c63d 100644 --- a/arch/arm64/boot/dts/amlogic/mesong12a.dtsi +++ b/arch/arm64/boot/dts/amlogic/mesong12a.dtsi @@ -1089,7 +1089,7 @@ cec_osd_string = "AML_MBOX"; /* Max Chars: 14 */ cec_version = <5>;/*5:1.4;6:2.0*/ port_num = <1>; - ee_cec; + /*ee_cec;*/ /*user default cec*/ arc_port_mask = <0x2>; interrupts = <0 203 1>; interrupt-names = "hdmi_aocecb"; diff --git a/arch/arm64/boot/dts/amlogic/txlx_t962e_r321.dts b/arch/arm64/boot/dts/amlogic/txlx_t962e_r321.dts index bb19f15280ba..a7e554c3fbb3 100644 --- a/arch/arm64/boot/dts/amlogic/txlx_t962e_r321.dts +++ b/arch/arm64/boot/dts/amlogic/txlx_t962e_r321.dts @@ -937,10 +937,13 @@ port_num = <3>; ee_cec; arc_port_mask = <0x2>; - interrupts = <0 205 1>; - interrupt-names = "hdmi_aocecb"; - pinctrl-names = "default"; - pinctrl-0=<&hdmitx_aocecb>; + interrupts = <0 205 1 + 0 199 1>; + interrupt-names = "hdmi_aocecb","hdmi_aocec"; + pinctrl-names = "default","hdmitx_aocecb","cec_pin_sleep"; + pinctrl-0=<&hdmitx_aocec>; + pinctrl-1=<&hdmitx_aocecb>; + pinctrl-2=<&hdmitx_aocecb>; reg = <0x0 0xFF80023c 0x0 0x4 0x0 0xFF800000 0x0 0x400>; }; diff --git a/arch/arm64/boot/dts/amlogic/txlx_t962x_r311_1g.dts b/arch/arm64/boot/dts/amlogic/txlx_t962x_r311_1g.dts index caabfb39fa8c..d878d30ff1f1 100644 --- a/arch/arm64/boot/dts/amlogic/txlx_t962x_r311_1g.dts +++ b/arch/arm64/boot/dts/amlogic/txlx_t962x_r311_1g.dts @@ -970,10 +970,13 @@ port_num = <4>; ee_cec; arc_port_mask = <0x2>; - interrupts = <0 205 1>; - interrupt-names = "hdmi_aocecb"; - pinctrl-names = "default"; - pinctrl-0=<&hdmitx_aocecb>; + interrupts = <0 205 1 + 0 199 1>; + interrupt-names = "hdmi_aocecb","hdmi_aocec"; + pinctrl-names = "default","hdmitx_aocecb","cec_pin_sleep"; + pinctrl-0=<&hdmitx_aocec>; + pinctrl-1=<&hdmitx_aocecb>; + pinctrl-2=<&hdmitx_aocecb>; reg = <0x0 0xFF80023c 0x0 0x4 0x0 0xFF800000 0x0 0x400>; }; diff --git a/arch/arm64/boot/dts/amlogic/txlx_t962x_r311_2g.dts b/arch/arm64/boot/dts/amlogic/txlx_t962x_r311_2g.dts index 6da9a9c006ca..9225163d766a 100644 --- a/arch/arm64/boot/dts/amlogic/txlx_t962x_r311_2g.dts +++ b/arch/arm64/boot/dts/amlogic/txlx_t962x_r311_2g.dts @@ -970,10 +970,13 @@ port_num = <4>; ee_cec; arc_port_mask = <0x2>; - interrupts = <0 205 1>; - interrupt-names = "hdmi_aocecb"; - pinctrl-names = "default"; - pinctrl-0=<&hdmitx_aocecb>; + interrupts = <0 205 1 + 0 199 1>; + interrupt-names = "hdmi_aocecb","hdmi_aocec"; + pinctrl-names = "default","hdmitx_aocecb","cec_pin_sleep"; + pinctrl-0=<&hdmitx_aocec>; + pinctrl-1=<&hdmitx_aocecb>; + pinctrl-2=<&hdmitx_aocecb>; reg = <0x0 0xFF80023c 0x0 0x4 0x0 0xFF800000 0x0 0x400>; }; diff --git a/arch/arm64/boot/dts/amlogic/txlx_t962x_r311_720p.dts b/arch/arm64/boot/dts/amlogic/txlx_t962x_r311_720p.dts index c552ef7ec4f2..2eceba841cb0 100644 --- a/arch/arm64/boot/dts/amlogic/txlx_t962x_r311_720p.dts +++ b/arch/arm64/boot/dts/amlogic/txlx_t962x_r311_720p.dts @@ -969,10 +969,13 @@ port_num = <4>; ee_cec; arc_port_mask = <0x2>; - interrupts = <0 205 1>; - interrupt-names = "hdmi_aocecb"; - pinctrl-names = "default"; - pinctrl-0=<&hdmitx_aocecb>; + interrupts = <0 205 1 + 0 199 1>; + interrupt-names = "hdmi_aocecb","hdmi_aocec"; + pinctrl-names = "default","hdmitx_aocecb","cec_pin_sleep"; + pinctrl-0=<&hdmitx_aocec>; + pinctrl-1=<&hdmitx_aocecb>; + pinctrl-2=<&hdmitx_aocecb>; reg = <0x0 0xFF80023c 0x0 0x4 0x0 0xFF800000 0x0 0x400>; }; diff --git a/drivers/amlogic/cec/hdmi_ao_cec.c b/drivers/amlogic/cec/hdmi_ao_cec.c index cbb8fb76eab4..e09131977615 100644 --- a/drivers/amlogic/cec/hdmi_ao_cec.c +++ b/drivers/amlogic/cec/hdmi_ao_cec.c @@ -94,6 +94,7 @@ struct cec_platform_data_s { /* global struct for tx and rx */ struct ao_cec_dev { unsigned long dev_type; + struct device_node *node; unsigned int port_num; unsigned int arc_port; unsigned int hal_flag; @@ -1127,49 +1128,93 @@ try_again: /* -------------------------------------------------------------------------- */ /* AO CEC0 config */ /* -------------------------------------------------------------------------- */ -void ao_cec_init(void) +static void ao_ceca_init(void) { unsigned long data32; unsigned int reg; + unsigned int chiptype; - if (get_meson_cpu_version(MESON_CPU_VERSION_LVL_MAJOR) >= - MESON_CPU_MAJOR_ID_GXBB) { - reg = (0 << 31) | - (0 << 30) | - (1 << 28) | /* clk_div0/clk_div1 in turn */ - ((732-1) << 12) | /* Div_tcnt1 */ - ((733-1) << 0); /* Div_tcnt0 */ - writel(reg, cec_dev->cec_reg + AO_RTC_ALT_CLK_CNTL0); - reg = (0 << 13) | - ((11-1) << 12) | - ((8-1) << 0); - writel(reg, cec_dev->cec_reg + AO_RTC_ALT_CLK_CNTL1); + chiptype = get_meson_cpu_version(MESON_CPU_VERSION_LVL_MAJOR); - reg = readl(cec_dev->cec_reg + AO_RTC_ALT_CLK_CNTL0); - reg |= (1 << 31); - writel(reg, cec_dev->cec_reg + AO_RTC_ALT_CLK_CNTL0); + /*CEC_INFO("chiptype=0x%x\n", chiptype);*/ + if (chiptype >= MESON_CPU_MAJOR_ID_GXBB) { + if (cec_dev->plat_data->ee_to_ao) { + reg = (0 << 31) | + (0 << 30) | + (1 << 28) | /* clk_div0/clk_div1 in turn */ + ((732-1) << 12) |/* Div_tcnt1 */ + ((733-1) << 0); /* Div_tcnt0 */ + writel(reg, cec_dev->cec_reg + AO_CEC_CLK_CNTL_REG0); + reg = (0 << 13) | + ((11-1) << 12) | + ((8-1) << 0); + writel(reg, cec_dev->cec_reg + AO_CEC_CLK_CNTL_REG1); + /*enable clk in*/ + reg = readl(cec_dev->cec_reg + AO_CEC_CLK_CNTL_REG0); + reg |= (1 << 31); + writel(reg, cec_dev->cec_reg + AO_CEC_CLK_CNTL_REG0); + /*enable clk out*/ + udelay(200); + reg |= (1 << 30); + writel(reg, cec_dev->cec_reg + AO_CEC_CLK_CNTL_REG0); + } else { + reg = (0 << 31) | + (0 << 30) | + (1 << 28) | /* clk_div0/clk_div1 in turn */ + ((732-1) << 12) |/* Div_tcnt1 */ + ((733-1) << 0); /* Div_tcnt0 */ + writel(reg, cec_dev->cec_reg + AO_RTC_ALT_CLK_CNTL0); + reg = (0 << 13) | + ((11-1) << 12) | + ((8-1) << 0); + writel(reg, cec_dev->cec_reg + AO_RTC_ALT_CLK_CNTL1); - udelay(200); - reg |= (1 << 30); - writel(reg, cec_dev->cec_reg + AO_RTC_ALT_CLK_CNTL0); + /*enable clk in*/ + reg = readl(cec_dev->cec_reg + AO_RTC_ALT_CLK_CNTL0); + reg |= (1 << 31); + writel(reg, cec_dev->cec_reg + AO_RTC_ALT_CLK_CNTL0); + /*enable clk out*/ + udelay(200); + reg |= (1 << 30); + writel(reg, cec_dev->cec_reg + AO_RTC_ALT_CLK_CNTL0); + } - reg = readl(cec_dev->cec_reg + AO_CRT_CLK_CNTL1); - reg |= (0x800 << 16); /* select cts_rtc_oscin_clk */ - writel(reg, cec_dev->cec_reg + AO_CRT_CLK_CNTL1); + if (cec_dev->plat_data->ee_to_ao) { + reg = readl(cec_dev->cec_reg + AO_RTI_PWR_CNTL_REG0); + reg |= (0x01 << 14);/* enable the crystal clock*/ + writel(reg, cec_dev->cec_reg + AO_RTI_PWR_CNTL_REG0); + } else { + reg = readl(cec_dev->cec_reg + AO_CRT_CLK_CNTL1); + reg |= (0x800 << 16);/* select cts_rtc_oscin_clk */ + writel(reg, cec_dev->cec_reg + AO_CRT_CLK_CNTL1); - reg = readl(cec_dev->cec_reg + AO_RTI_PWR_CNTL_REG0); - reg &= ~(0x07 << 10); - reg |= (0x04 << 10); /* XTAL generate 32k */ - writel(reg, cec_dev->cec_reg + AO_RTI_PWR_CNTL_REG0); + reg = readl(cec_dev->cec_reg + AO_RTI_PWR_CNTL_REG0); + reg &= ~(0x07 << 10); + reg |= (0x04 << 10);/* XTAL generate 32k */ + writel(reg, cec_dev->cec_reg + AO_RTI_PWR_CNTL_REG0); + } } - data32 = 0; - data32 |= 0 << 1; /* [2:1] cntl_clk: */ + if (cec_dev->plat_data->ee_to_ao) { + data32 = 0; + data32 |= (7 << 12); /* filter_del */ + data32 |= (1 << 8); /* filter_tick: 1us */ + data32 |= (1 << 3); /* enable system clock*/ + data32 |= 0 << 1; /* [2:1] cntl_clk: */ /* 0=Disable clk (Power-off mode); */ - /* 1=Enable gated clock (Normal mode); */ - /* 2=Enable free-run clk (Debug mode). */ - data32 |= 1 << 0; /* [0] sw_reset: 1=Reset */ - writel(data32, cec_dev->cec_reg + AO_CEC_GEN_CNTL); + /* 1=Enable gated clock (Normal mode);*/ + /* 2=Enable free-run clk (Debug mode).*/ + data32 |= 1 << 0; /* [0] sw_reset: 1=Reset*/ + writel(data32, cec_dev->cec_reg + AO_CEC_GEN_CNTL); + } else { + data32 = 0; + data32 |= 0 << 1; /* [2:1] cntl_clk:*/ + /* 0=Disable clk (Power-off mode);*/ + /* 1=Enable gated clock (Normal mode);*/ + /* 2=Enable free-run clk (Debug mode).*/ + data32 |= 1 << 0; /* [0] sw_reset: 1=Reset */ + writel(data32, cec_dev->cec_reg + AO_CEC_GEN_CNTL); + } /* Enable gated clock (Normal mode). */ cec_set_reg_bits(AO_CEC_GEN_CNTL, 1, 1, 1); /* Release SW reset */ @@ -1293,13 +1338,13 @@ static void cec_pre_init(void) if (ee_cec) { cecrx_hw_init(); - return; - } - ao_cec_init(); + } else { + ao_ceca_init(); - cec_arbit_bit_time_set(3, 0x118, 0); - cec_arbit_bit_time_set(5, 0x000, 0); - cec_arbit_bit_time_set(7, 0x2aa, 0); + cec_arbit_bit_time_set(3, 0x118, 0); + cec_arbit_bit_time_set(5, 0x000, 0); + cec_arbit_bit_time_set(7, 0x2aa, 0); + } } static int cec_late_check_rx_buffer(void) @@ -1317,9 +1362,10 @@ static int cec_late_check_rx_buffer(void) CEC_INFO("buffer got unrecorgnized msg\n"); cec_rx_buf_clear(); return 0; + } else { + mod_delayed_work(cec_dev->cec_thread, dwork, 0); + return 1; } - mod_delayed_work(cec_dev->cec_thread, dwork, 0); - return 1; } void cec_key_report(int suspend) @@ -2431,7 +2477,7 @@ static int aml_cec_probe(struct platform_device *pdev) struct device_node *node = pdev->dev.of_node; int irq_idx = 0, r; const char *irq_name = NULL; - struct pinctrl *p; + struct pinctrl *pin; struct vendor_info_data *vend; struct resource *res; resource_size_t *base; @@ -2449,6 +2495,7 @@ static int aml_cec_probe(struct platform_device *pdev) cec_dev->dbg_dev = &pdev->dev; cec_dev->tx_dev = get_hdmitx_device(); cec_dev->cpu_type = get_cpu_type(); + cec_dev->node = pdev->dev.of_node; phy_addr_test = 0; /* cdev registe */ @@ -2526,18 +2573,41 @@ static int aml_cec_probe(struct platform_device *pdev) ee_cec = 1; else ee_cec = 0; - CEC_INFO("using EE cec:%d\n", ee_cec); + CEC_INFO("using cec:%d\n", ee_cec); + /* pinmux set */ if (of_get_property(node, "pinctrl-names", NULL)) { - r = of_property_read_string(node, - "pinctrl-names", - &cec_dev->pin_name); - if ((!r) && strcmp(cec_dev->pin_name, "default")) { - CEC_INFO("%s pin name:%s\n", __func__, - cec_dev->pin_name); - p = devm_pinctrl_get_select(&pdev->dev, - cec_dev->pin_name); + pin = devm_pinctrl_get(&pdev->dev); + /*get sleep state*/ + cec_dev->dbg_dev->pins->sleep_state = + pinctrl_lookup_state(pin, "cec_pin_sleep"); + if (IS_ERR(cec_dev->dbg_dev->pins->sleep_state)) + CEC_ERR("get sleep state error!\n"); + /*get active state*/ + if (ee_cec) { + cec_dev->dbg_dev->pins->default_state = + pinctrl_lookup_state(pin, "hdmitx_aocecb"); + if (IS_ERR(cec_dev->dbg_dev->pins->default_state)) { + CEC_ERR("get aocecb error!\n"); + cec_dev->dbg_dev->pins->default_state = + pinctrl_lookup_state(pin, "default"); + if (IS_ERR( + cec_dev->dbg_dev->pins->default_state)) + CEC_ERR("get default error0\n"); + CEC_ERR("use default cec\n"); + /*force use default*/ + ee_cec = 0; + } + } else { + cec_dev->dbg_dev->pins->default_state = + pinctrl_lookup_state(pin, "default"); + if (IS_ERR(cec_dev->dbg_dev->pins->default_state)) + CEC_ERR("get default error1!\n"); } + /*select pin state*/ + ret = pinctrl_pm_select_default_state(&pdev->dev); + if (ret > 0) + CEC_ERR("select state error:0x%x\n", ret); } res = platform_get_resource(pdev, IORESOURCE_MEM, 0); @@ -2614,8 +2684,12 @@ static int aml_cec_probe(struct platform_device *pdev) /* irq set */ cec_irq_enable(false); - irq_idx = of_irq_get(node, 0); + if (ee_cec) + irq_idx = of_irq_get(node, 0); + else + irq_idx = of_irq_get(node, 1); cec_dev->irq_cec = irq_idx; + /*CEC_INFO("irq no:%d\n", irq_idx);*/ if (of_get_property(node, "interrupt-names", NULL)) { r = of_property_read_string(node, "interrupt-names", &irq_name); if (!r && !ee_cec) { @@ -2711,15 +2785,27 @@ static void aml_cec_pm_complete(struct device *dev) static int aml_cec_suspend_noirq(struct device *dev) { + int ret = 0; + + CEC_INFO("cec suspend noirq\n"); + if (!IS_ERR(cec_dev->dbg_dev->pins->sleep_state)) + ret = pinctrl_pm_select_sleep_state(cec_dev->dbg_dev); + else + CEC_ERR("pinctrl sleep_state error\n"); return 0; } static int aml_cec_resume_noirq(struct device *dev) { + int ret = 0; + CEC_INFO("cec resume noirq!\n"); cec_dev->cec_info.power_status = TRANS_STANDBY_TO_ON; cec_dev->cec_suspend = CEC_POWER_RESUME; - + if (!IS_ERR(cec_dev->dbg_dev->pins->default_state)) + ret = pinctrl_pm_select_default_state(cec_dev->dbg_dev); + else + CEC_ERR("pinctrl default_state error\n"); return 0; }