[source] ipq806x: route gpio interrupts to APPS processor through scm firmware
LEDE Commits
lede-commits at lists.infradead.org
Mon Mar 20 00:34:57 PDT 2017
blogic pushed a commit to source.git, branch master:
https://git.lede-project.org/ef4ca01d6fa762d9cfc17138bc7dc3a4eb5b83cb
commit ef4ca01d6fa762d9cfc17138bc7dc3a4eb5b83cb
Author: Pavel Kubelun <be.dissent at gmail.com>
AuthorDate: Sun Mar 19 07:59:26 2017 -0400
ipq806x: route gpio interrupts to APPS processor through scm firmware
For IPQ806x targets, TZ protects the registers that are used to
configure the routing of interrupts to a target processor.
To resolve this, this patch uses scm call to route GPIO interrupts
to application processor. Also the scm call interface is changed.
Signed-off-by: Pavel Kubelun <be.dissent at gmail.com>
---
...om-use-scm_call-to-route-GPIO-irq-to-Apps.patch | 166 +++++++++++++++++++++
1 file changed, 166 insertions(+)
diff --git a/target/linux/ipq806x/patches-4.9/0073-pinctrl-qom-use-scm_call-to-route-GPIO-irq-to-Apps.patch b/target/linux/ipq806x/patches-4.9/0073-pinctrl-qom-use-scm_call-to-route-GPIO-irq-to-Apps.patch
new file mode 100644
index 0000000..2eac44d
--- /dev/null
+++ b/target/linux/ipq806x/patches-4.9/0073-pinctrl-qom-use-scm_call-to-route-GPIO-irq-to-Apps.patch
@@ -0,0 +1,166 @@
+From 2034addc7e193dc81d7ca60d8884832751b76758 Mon Sep 17 00:00:00 2001
+From: Ajay Kishore <akisho at codeaurora.org>
+Date: Tue, 24 Jan 2017 14:14:16 +0530
+Subject: pinctrl: qcom: use scm_call to route GPIO irq to Apps
+
+For IPQ806x targets, TZ protects the registers that are used to
+configure the routing of interrupts to a target processor.
+To resolve this, this patch uses scm call to route GPIO interrupts
+to application processor. Also the scm call interface is changed.
+
+Change-Id: Ib6c06829d04bc8c20483c36e63da92e26cdef9ce
+Signed-off-by: Ajay Kishore <akisho at codeaurora.org>
+---
+ drivers/firmware/qcom_scm-32.c | 17 +++++++++++++++++
+ drivers/firmware/qcom_scm-64.c | 9 +++++++++
+ drivers/firmware/qcom_scm.c | 13 +++++++++++++
+ drivers/firmware/qcom_scm.h | 8 ++++++++
+ drivers/pinctrl/qcom/pinctrl-msm.c | 34 ++++++++++++++++++++++++++++------
+ include/linux/qcom_scm.h | 3 ++-
+ 6 files changed, 77 insertions(+), 7 deletions(-)
+
+--- a/drivers/firmware/qcom_scm-32.c
++++ b/drivers/firmware/qcom_scm-32.c
+@@ -560,3 +560,21 @@ int __qcom_scm_pas_mss_reset(struct devi
+
+ return ret ? : le32_to_cpu(out);
+ }
++
++int __qcom_scm_pinmux_read(u32 svc_id, u32 cmd_id, u32 arg1)
++{
++ s32 ret;
++
++ ret = qcom_scm_call_atomic1(svc_id, cmd_id, arg1);
++
++ return ret;
++}
++
++int __qcom_scm_pinmux_write(u32 svc_id, u32 cmd_id, u32 arg1, u32 arg2)
++{
++ s32 ret;
++
++ ret = qcom_scm_call_atomic2(svc_id, cmd_id, arg1, arg2);
++
++ return ret;
++ }
+--- a/drivers/firmware/qcom_scm-64.c
++++ b/drivers/firmware/qcom_scm-64.c
+@@ -358,3 +358,12 @@ int __qcom_scm_pas_mss_reset(struct devi
+
+ return ret ? : res.a1;
+ }
++int __qcom_scm_pinmux_read(u32 svc_id, u32 cmd_id, u32 arg1)
++{
++ return -ENOTSUPP;
++}
++
++int __qcom_scm_pinmux_write(u32 svc_id, u32 cmd_id, u32 arg1, u32 arg2)
++{
++ return -ENOTSUPP;
++}
+--- a/drivers/firmware/qcom_scm.c
++++ b/drivers/firmware/qcom_scm.c
+@@ -443,3 +443,16 @@ static int __init qcom_scm_init(void)
+ return platform_driver_register(&qcom_scm_driver);
+ }
+ subsys_initcall(qcom_scm_init);
++
++int qcom_scm_pinmux_read(u32 arg1)
++{
++ return __qcom_scm_pinmux_read(SCM_SVC_IO_ACCESS, SCM_IO_READ, arg1);
++}
++EXPORT_SYMBOL(qcom_scm_pinmux_read);
++
++int qcom_scm_pinmux_write(u32 arg1, u32 arg2)
++{
++ return __qcom_scm_pinmux_write(SCM_SVC_IO_ACCESS, SCM_IO_WRITE,
++ arg1, arg2);
++}
++EXPORT_SYMBOL(qcom_scm_pinmux_write);
+--- a/drivers/firmware/qcom_scm.h
++++ b/drivers/firmware/qcom_scm.h
+@@ -56,6 +56,13 @@ extern int __qcom_scm_pas_auth_and_rese
+ extern int __qcom_scm_pas_shutdown(struct device *dev, u32 peripheral);
+ extern int __qcom_scm_pas_mss_reset(struct device *dev, bool reset);
+
++#define SCM_IO_READ 1
++#define SCM_IO_WRITE 2
++#define SCM_SVC_IO_ACCESS 0x5
++
++s32 __qcom_scm_pinmux_read(u32 svc_id, u32 cmd_id, u32 arg1);
++s32 __qcom_scm_pinmux_write(u32 svc_id, u32 cmd_id, u32 arg1, u32 arg2);
++
+ /* common error codes */
+ #define QCOM_SCM_V2_EBUSY -12
+ #define QCOM_SCM_ENOMEM -5
+--- a/drivers/pinctrl/qcom/pinctrl-msm.c
++++ b/drivers/pinctrl/qcom/pinctrl-msm.c
+@@ -30,7 +30,8 @@
+ #include <linux/reboot.h>
+ #include <linux/pm.h>
+ #include <linux/log2.h>
+-
++#include <linux/qcom_scm.h>
++#include <linux/io.h>
+ #include "../core.h"
+ #include "../pinconf.h"
+ #include "pinctrl-msm.h"
+@@ -639,6 +640,9 @@ static int msm_gpio_irq_set_type(struct
+ const struct msm_pingroup *g;
+ unsigned long flags;
+ u32 val;
++ u32 addr;
++ int ret;
++ const __be32 *reg;
+
+ g = &pctrl->soc->groups[d->hwirq];
+
+@@ -652,11 +656,30 @@ static int msm_gpio_irq_set_type(struct
+ else
+ clear_bit(d->hwirq, pctrl->dual_edge_irqs);
+
++ ret = of_device_is_compatible(pctrl->dev->of_node,
++ "qcom,ipq8064-pinctrl");
+ /* Route interrupts to application cpu */
+- val = readl(pctrl->regs + g->intr_target_reg);
+- val &= ~(7 << g->intr_target_bit);
+- val |= g->intr_target_kpss_val << g->intr_target_bit;
+- writel(val, pctrl->regs + g->intr_target_reg);
++ if (!ret) {
++ val = readl(pctrl->regs + g->intr_target_reg);
++ val &= ~(7 << g->intr_target_bit);
++ val |= g->intr_target_kpss_val << g->intr_target_bit;
++ writel(val, pctrl->regs + g->intr_target_reg);
++ } else {
++ reg = of_get_property(pctrl->dev->of_node, "reg", NULL);
++ if (reg) {
++ addr = be32_to_cpup(reg) + g->intr_target_reg;
++ val = qcom_scm_pinmux_read(addr);
++ __iormb();
++
++ val &= ~(7 << g->intr_target_bit);
++ val |= g->intr_target_kpss_val << g->intr_target_bit;
++
++ __iowmb();
++ ret = qcom_scm_pinmux_write(addr, val);
++ if (ret)
++ pr_err("\n Routing interrupts to Apps proc failed");
++ }
++ }
+
+ /* Update configuration for gpio.
+ * RAW_STATUS_EN is left on for all gpio irqs. Due to the
+@@ -930,4 +953,3 @@ int msm_pinctrl_remove(struct platform_d
+ return 0;
+ }
+ EXPORT_SYMBOL(msm_pinctrl_remove);
+-
+--- a/include/linux/qcom_scm.h
++++ b/include/linux/qcom_scm.h
+@@ -46,4 +46,6 @@ extern void qcom_scm_cpu_power_down(u32
+
+ extern u32 qcom_scm_get_version(void);
+
++extern s32 qcom_scm_pinmux_read(u32 arg1);
++extern s32 qcom_scm_pinmux_write(u32 arg1, u32 arg2);
+ #endif
More information about the lede-commits
mailing list