soc: mediatek: pm_domains: Make bus protection generic
authorMatthias Brugger <mbrugger@suse.com>
Fri, 30 Oct 2020 11:36:11 +0000 (12:36 +0100)
committerMatthias Brugger <matthias.bgg@gmail.com>
Fri, 27 Nov 2020 11:04:42 +0000 (12:04 +0100)
Bus protection is not exclusively done by calling the infracfg misc driver.
Make the calls for setting and clearing the bus protection generic so
that we can use other blocks for it as well.

Signed-off-by: Matthias Brugger <mbrugger@suse.com>
Signed-off-by: Enric Balletbo i Serra <enric.balletbo@collabora.com>
Link: https://lore.kernel.org/r/20201030113622.201188-6-enric.balletbo@collabora.com
Signed-off-by: Matthias Brugger <matthias.bgg@gmail.com>
drivers/soc/mediatek/Kconfig
drivers/soc/mediatek/mtk-infracfg.c
drivers/soc/mediatek/mtk-pm-domains.c
include/linux/soc/mediatek/infracfg.h

index 68d800f..67cef12 100644 (file)
@@ -48,7 +48,6 @@ config MTK_SCPSYS_PM_DOMAINS
        bool "MediaTek SCPSYS generic power domain"
        default ARCH_MEDIATEK
        depends on PM
-       depends on MTK_INFRACFG
        select PM_GENERIC_DOMAINS
        select REGMAP
        help
index 4a12379..0590b68 100644 (file)
 #define MTK_POLL_DELAY_US   10
 #define MTK_POLL_TIMEOUT    (jiffies_to_usecs(HZ))
 
-#define INFRA_TOPAXI_PROTECTEN         0x0220
-#define INFRA_TOPAXI_PROTECTSTA1       0x0228
-#define INFRA_TOPAXI_PROTECTEN_SET     0x0260
-#define INFRA_TOPAXI_PROTECTEN_CLR     0x0264
-
 /**
  * mtk_infracfg_set_bus_protection - enable bus protection
  * @infracfg: The infracfg regmap
index 06a16e4..6122701 100644 (file)
@@ -86,18 +86,24 @@ static int scpsys_sram_disable(struct scpsys_domain *pd)
                                        MTK_POLL_TIMEOUT);
 }
 
-static int scpsys_bus_protect_enable(struct scpsys_domain *pd)
+static int _scpsys_bus_protect_enable(const struct scpsys_bus_prot_data *bpd, struct regmap *regmap)
 {
-       const struct scpsys_bus_prot_data *bpd = pd->data->bp_infracfg;
        int i, ret;
 
        for (i = 0; i < SPM_MAX_BUS_PROT_DATA; i++) {
-               if (!bpd[i].bus_prot_mask)
+               u32 val, mask = bpd[i].bus_prot_mask;
+
+               if (!mask)
                        break;
 
-               ret = mtk_infracfg_set_bus_protection(pd->infracfg,
-                                                     bpd[i].bus_prot_mask,
-                                                     bpd[i].bus_prot_reg_update);
+               if (bpd[i].bus_prot_reg_update)
+                       regmap_set_bits(regmap, bpd[i].bus_prot_set, mask);
+               else
+                       regmap_write(regmap, INFRA_TOPAXI_PROTECTEN_SET, mask);
+
+               ret = regmap_read_poll_timeout(regmap, INFRA_TOPAXI_PROTECTSTA1,
+                                              val, (val & mask) == mask,
+                                              MTK_POLL_DELAY_US, MTK_POLL_TIMEOUT);
                if (ret)
                        return ret;
        }
@@ -105,18 +111,34 @@ static int scpsys_bus_protect_enable(struct scpsys_domain *pd)
        return 0;
 }
 
-static int scpsys_bus_protect_disable(struct scpsys_domain *pd)
+static int scpsys_bus_protect_enable(struct scpsys_domain *pd)
+{
+       int ret;
+
+       ret = _scpsys_bus_protect_enable(pd->data->bp_infracfg, pd->infracfg);
+
+       return ret;
+}
+
+static int _scpsys_bus_protect_disable(const struct scpsys_bus_prot_data *bpd,
+                                      struct regmap *regmap)
 {
-       const struct scpsys_bus_prot_data *bpd = pd->data->bp_infracfg;
        int i, ret;
 
-       for (i = SPM_MAX_BUS_PROT_DATA; i > 0; i--) {
-               if (!bpd[i].bus_prot_mask)
+       for (i = SPM_MAX_BUS_PROT_DATA - 1; i >= 0; i--) {
+               u32 val, mask = bpd[i].bus_prot_mask;
+
+               if (!mask)
                        continue;
 
-               ret = mtk_infracfg_clear_bus_protection(pd->infracfg,
-                                                       bpd[i].bus_prot_mask,
-                                                       bpd[i].bus_prot_reg_update);
+               if (bpd[i].bus_prot_reg_update)
+                       regmap_clear_bits(regmap, bpd[i].bus_prot_clr, mask);
+               else
+                       regmap_write(regmap, INFRA_TOPAXI_PROTECTEN_CLR, mask);
+
+               ret = regmap_read_poll_timeout(regmap, INFRA_TOPAXI_PROTECTSTA1,
+                                              val, !(val & mask),
+                                              MTK_POLL_DELAY_US, MTK_POLL_TIMEOUT);
                if (ret)
                        return ret;
        }
@@ -124,6 +146,15 @@ static int scpsys_bus_protect_disable(struct scpsys_domain *pd)
        return 0;
 }
 
+static int scpsys_bus_protect_disable(struct scpsys_domain *pd)
+{
+       int ret;
+
+       ret = _scpsys_bus_protect_disable(pd->data->bp_infracfg, pd->infracfg);
+
+       return ret;
+}
+
 static int scpsys_power_on(struct generic_pm_domain *genpd)
 {
        struct scpsys_domain *pd = container_of(genpd, struct scpsys_domain, genpd);
index 233463d..5bcaab7 100644 (file)
 #define MT7622_TOP_AXI_PROT_EN_WB              (BIT(2) | BIT(6) | \
                                                 BIT(7) | BIT(8))
 
+#define INFRA_TOPAXI_PROTECTEN                 0x0220
+#define INFRA_TOPAXI_PROTECTSTA1               0x0228
+#define INFRA_TOPAXI_PROTECTEN_SET             0x0260
+#define INFRA_TOPAXI_PROTECTEN_CLR             0x0264
+
 #define REG_INFRA_MISC                         0xf00
 #define F_DDR_4GB_SUPPORT_EN                   BIT(13)