summaryrefslogtreecommitdiff
path: root/drivers/pinctrl
diff options
context:
space:
mode:
authorUlrich Hecht <uli+renesas@fpond.eu>2021-01-12 17:59:07 +0100
committerGeert Uytterhoeven <geert+renesas@glider.be>2021-01-14 12:06:12 +0100
commite127ef2ed0a6099ca6ccc55ff11a812514b6aee6 (patch)
tree023829f445a619bebb33775aa540dfde7a73c240 /drivers/pinctrl
parent88a1590b1407207a51788d56746f46cbd6e6ab4e (diff)
pinctrl: renesas: Implement unlock register masks
The V3U SoC has several unlock registers, one per register group. They reside at offset zero in each 0x200 bytes-sized block. To avoid adding yet another table to the PFC implementation, this patch adds the option to specify an address mask instead of the fixed address in sh_pfc_soc_info::unlock_reg. Signed-off-by: Ulrich Hecht <uli+renesas@fpond.eu> Tested-by: Wolfram Sang <wsa+renesas@sang-engineering.com> Link: https://lore.kernel.org/r/20210112165912.30876-2-uli+renesas@fpond.eu Signed-off-by: Geert Uytterhoeven <geert+renesas@glider.be>
Diffstat (limited to 'drivers/pinctrl')
-rw-r--r--drivers/pinctrl/renesas/core.c28
-rw-r--r--drivers/pinctrl/renesas/sh_pfc.h2
2 files changed, 19 insertions, 11 deletions
diff --git a/drivers/pinctrl/renesas/core.c b/drivers/pinctrl/renesas/core.c
index 291d2c673b8f..979407f2cac6 100644
--- a/drivers/pinctrl/renesas/core.c
+++ b/drivers/pinctrl/renesas/core.c
@@ -175,13 +175,25 @@ u32 sh_pfc_read(struct sh_pfc *pfc, u32 reg)
return sh_pfc_read_raw_reg(sh_pfc_phys_to_virt(pfc, reg), 32);
}
-void sh_pfc_write(struct sh_pfc *pfc, u32 reg, u32 data)
+static void sh_pfc_unlock_reg(struct sh_pfc *pfc, u32 reg, u32 data)
{
- if (pfc->info->unlock_reg)
- sh_pfc_write_raw_reg(
- sh_pfc_phys_to_virt(pfc, pfc->info->unlock_reg), 32,
- ~data);
+ u32 unlock;
+
+ if (!pfc->info->unlock_reg)
+ return;
+ if (pfc->info->unlock_reg >= 0x80000000UL)
+ unlock = pfc->info->unlock_reg;
+ else
+ /* unlock_reg is a mask */
+ unlock = reg & ~pfc->info->unlock_reg;
+
+ sh_pfc_write_raw_reg(sh_pfc_phys_to_virt(pfc, unlock), 32, ~data);
+}
+
+void sh_pfc_write(struct sh_pfc *pfc, u32 reg, u32 data)
+{
+ sh_pfc_unlock_reg(pfc, reg, data);
sh_pfc_write_raw_reg(sh_pfc_phys_to_virt(pfc, reg), 32, data);
}
@@ -227,11 +239,7 @@ static void sh_pfc_write_config_reg(struct sh_pfc *pfc,
data &= mask;
data |= value;
- if (pfc->info->unlock_reg)
- sh_pfc_write_raw_reg(
- sh_pfc_phys_to_virt(pfc, pfc->info->unlock_reg), 32,
- ~data);
-
+ sh_pfc_unlock_reg(pfc, crp->reg, data);
sh_pfc_write_raw_reg(mapped_reg, crp->reg_width, data);
}
diff --git a/drivers/pinctrl/renesas/sh_pfc.h b/drivers/pinctrl/renesas/sh_pfc.h
index dc484c13f59c..1404bd897d25 100644
--- a/drivers/pinctrl/renesas/sh_pfc.h
+++ b/drivers/pinctrl/renesas/sh_pfc.h
@@ -300,7 +300,7 @@ struct sh_pfc_soc_info {
const u16 *pinmux_data;
unsigned int pinmux_data_size;
- u32 unlock_reg;
+ u32 unlock_reg; /* can be literal address or mask */
};
extern const struct sh_pfc_soc_info emev2_pinmux_info;