diff options
author | Linus Torvalds <torvalds@linux-foundation.org> | 2023-02-27 10:04:49 -0800 |
---|---|---|
committer | Linus Torvalds <torvalds@linux-foundation.org> | 2023-02-27 10:04:49 -0800 |
commit | 11c70529983e8136ea1bd5c32e4f9cd14503c644 (patch) | |
tree | 8e36f8397a68a4906fd49b72de8c7efb9b0e2a0d /drivers/soc/renesas | |
parent | d40b2f4c94f221bd5aab205f945e6f88d3df0929 (diff) | |
parent | 524af30c931382726b6a46ee4f392fb6e60f8a03 (diff) |
Merge tag 'soc-drivers-6.3' of git://git.kernel.org/pub/scm/linux/kernel/git/soc/soc
Pull ARM SoC driver updates from Arnd Bergmann:
"As usual, there are lots of minor driver changes across SoC platforms
from NXP, Amlogic, AMD Zynq, Mediatek, Qualcomm, Apple and Samsung.
These usually add support for additional chip variations in existing
drivers, but also add features or bugfixes.
The SCMI firmware subsystem gains a unified raw userspace interface
through debugfs, which can be used for validation purposes.
Newly added drivers include:
- New power management drivers for StarFive JH7110, Allwinner D1 and
Renesas RZ/V2M
- A driver for Qualcomm battery and power supply status
- A SoC device driver for identifying Nuvoton WPCM450 chips
- A regulator coupler driver for Mediatek MT81xxv"
* tag 'soc-drivers-6.3' of git://git.kernel.org/pub/scm/linux/kernel/git/soc/soc: (165 commits)
power: supply: Introduce Qualcomm PMIC GLINK power supply
soc: apple: rtkit: Do not copy the reg state structure to the stack
soc: sunxi: SUN20I_PPU should depend on PM
memory: renesas-rpc-if: Remove redundant division of dummy
soc: qcom: socinfo: Add IDs for IPQ5332 and its variant
dt-bindings: arm: qcom,ids: Add IDs for IPQ5332 and its variant
dt-bindings: power: qcom,rpmpd: add RPMH_REGULATOR_LEVEL_LOW_SVS_L1
firmware: qcom_scm: Move qcom_scm.h to include/linux/firmware/qcom/
MAINTAINERS: Update qcom CPR maintainer entry
dt-bindings: firmware: document Qualcomm SM8550 SCM
dt-bindings: firmware: qcom,scm: add qcom,scm-sa8775p compatible
soc: qcom: socinfo: Add Soc IDs for IPQ8064 and variants
dt-bindings: arm: qcom,ids: Add Soc IDs for IPQ8064 and variants
soc: qcom: socinfo: Add support for new field in revision 17
soc: qcom: smd-rpm: Add IPQ9574 compatible
soc: qcom: pmic_glink: remove redundant calculation of svid
soc: qcom: stats: Populate all subsystem debugfs files
dt-bindings: soc: qcom,rpmh-rsc: Update to allow for generic nodes
soc: qcom: pmic_glink: add CONFIG_NET/CONFIG_OF dependencies
soc: qcom: pmic_glink: Introduce altmode support
...
Diffstat (limited to 'drivers/soc/renesas')
-rw-r--r-- | drivers/soc/renesas/Kconfig | 4 | ||||
-rw-r--r-- | drivers/soc/renesas/Makefile | 1 | ||||
-rw-r--r-- | drivers/soc/renesas/pwc-rzv2m.c | 141 | ||||
-rw-r--r-- | drivers/soc/renesas/r8a779g0-sysc.c | 1 |
4 files changed, 147 insertions, 0 deletions
diff --git a/drivers/soc/renesas/Kconfig b/drivers/soc/renesas/Kconfig index 660498252ec5..4e8b51ba2266 100644 --- a/drivers/soc/renesas/Kconfig +++ b/drivers/soc/renesas/Kconfig @@ -330,6 +330,7 @@ config ARCH_R9A09G011 bool "ARM64 Platform support for RZ/V2M" select PM select PM_GENERIC_DOMAINS + select PWC_RZV2M help This enables support for the Renesas RZ/V2M SoC. @@ -345,6 +346,9 @@ config ARCH_R9A07G043 endif # RISCV +config PWC_RZV2M + bool "Renesas RZ/V2M PWC support" if COMPILE_TEST + config RST_RCAR bool "Reset Controller support for R-Car" if COMPILE_TEST diff --git a/drivers/soc/renesas/Makefile b/drivers/soc/renesas/Makefile index 535868c9c7e4..6e4e77b0afff 100644 --- a/drivers/soc/renesas/Makefile +++ b/drivers/soc/renesas/Makefile @@ -32,6 +32,7 @@ obj-$(CONFIG_ARCH_R9A06G032) += r9a06g032-smp.o endif # Family +obj-$(CONFIG_PWC_RZV2M) += pwc-rzv2m.o obj-$(CONFIG_RST_RCAR) += rcar-rst.o obj-$(CONFIG_SYSC_RCAR) += rcar-sysc.o obj-$(CONFIG_SYSC_RCAR_GEN4) += rcar-gen4-sysc.o diff --git a/drivers/soc/renesas/pwc-rzv2m.c b/drivers/soc/renesas/pwc-rzv2m.c new file mode 100644 index 000000000000..c83bdbdabb64 --- /dev/null +++ b/drivers/soc/renesas/pwc-rzv2m.c @@ -0,0 +1,141 @@ +// SPDX-License-Identifier: GPL-2.0-only +/* + * Copyright (C) 2023 Renesas Electronics Corporation + */ + +#include <linux/delay.h> +#include <linux/gpio/driver.h> +#include <linux/platform_device.h> +#include <linux/reboot.h> + +#define PWC_PWCRST 0x00 +#define PWC_PWCCKEN 0x04 +#define PWC_PWCCTL 0x50 +#define PWC_GPIO 0x80 + +#define PWC_PWCRST_RSTSOFTAX 0x1 +#define PWC_PWCCKEN_ENGCKMAIN 0x1 +#define PWC_PWCCTL_PWOFF 0x1 + +struct rzv2m_pwc_priv { + void __iomem *base; + struct device *dev; + struct gpio_chip gp; + DECLARE_BITMAP(ch_en_bits, 2); +}; + +static void rzv2m_pwc_gpio_set(struct gpio_chip *chip, unsigned int offset, + int value) +{ + struct rzv2m_pwc_priv *priv = gpiochip_get_data(chip); + u32 reg; + + /* BIT 16 enables write to BIT 0, and BIT 17 enables write to BIT 1 */ + reg = BIT(offset + 16); + if (value) + reg |= BIT(offset); + + writel(reg, priv->base + PWC_GPIO); + + assign_bit(offset, priv->ch_en_bits, value); +} + +static int rzv2m_pwc_gpio_get(struct gpio_chip *chip, unsigned int offset) +{ + struct rzv2m_pwc_priv *priv = gpiochip_get_data(chip); + + return test_bit(offset, priv->ch_en_bits); +} + +static int rzv2m_pwc_gpio_direction_output(struct gpio_chip *gc, + unsigned int nr, int value) +{ + if (nr > 1) + return -EINVAL; + + rzv2m_pwc_gpio_set(gc, nr, value); + + return 0; +} + +static const struct gpio_chip rzv2m_pwc_gc = { + .label = "gpio_rzv2m_pwc", + .owner = THIS_MODULE, + .get = rzv2m_pwc_gpio_get, + .set = rzv2m_pwc_gpio_set, + .direction_output = rzv2m_pwc_gpio_direction_output, + .can_sleep = false, + .ngpio = 2, + .base = -1, +}; + +static int rzv2m_pwc_poweroff(struct sys_off_data *data) +{ + struct rzv2m_pwc_priv *priv = data->cb_data; + + writel(PWC_PWCRST_RSTSOFTAX, priv->base + PWC_PWCRST); + writel(PWC_PWCCKEN_ENGCKMAIN, priv->base + PWC_PWCCKEN); + writel(PWC_PWCCTL_PWOFF, priv->base + PWC_PWCCTL); + + mdelay(150); + + dev_err(priv->dev, "Failed to power off the system"); + + return NOTIFY_DONE; +} + +static int rzv2m_pwc_probe(struct platform_device *pdev) +{ + struct rzv2m_pwc_priv *priv; + int ret; + + priv = devm_kzalloc(&pdev->dev, sizeof(*priv), GFP_KERNEL); + if (!priv) + return -ENOMEM; + + priv->base = devm_platform_ioremap_resource(pdev, 0); + if (IS_ERR(priv->base)) + return PTR_ERR(priv->base); + + /* + * The register used by this driver cannot be read, therefore set the + * outputs to their default values and initialize priv->ch_en_bits + * accordingly. BIT 16 enables write to BIT 0, BIT 17 enables write to + * BIT 1, and the default value of both BIT 0 and BIT 1 is 0. + */ + writel(BIT(17) | BIT(16), priv->base + PWC_GPIO); + bitmap_zero(priv->ch_en_bits, 2); + + priv->gp = rzv2m_pwc_gc; + priv->gp.parent = pdev->dev.parent; + priv->gp.fwnode = dev_fwnode(&pdev->dev); + + ret = devm_gpiochip_add_data(&pdev->dev, &priv->gp, priv); + if (ret) + return ret; + + if (device_property_read_bool(&pdev->dev, "renesas,rzv2m-pwc-power")) + ret = devm_register_power_off_handler(&pdev->dev, + rzv2m_pwc_poweroff, priv); + + return ret; +} + +static const struct of_device_id rzv2m_pwc_of_match[] = { + { .compatible = "renesas,rzv2m-pwc" }, + { /* sentinel */ } +}; +MODULE_DEVICE_TABLE(of, rzv2m_pwc_of_match); + +static struct platform_driver rzv2m_pwc_driver = { + .probe = rzv2m_pwc_probe, + .driver = { + .name = "rzv2m_pwc", + .of_match_table = of_match_ptr(rzv2m_pwc_of_match), + }, +}; +module_platform_driver(rzv2m_pwc_driver); + +MODULE_LICENSE("GPL"); +MODULE_AUTHOR("Fabrizio Castro <castro.fabrizio.jz@renesas.com>"); +MODULE_DESCRIPTION("Renesas RZ/V2M PWC driver"); diff --git a/drivers/soc/renesas/r8a779g0-sysc.c b/drivers/soc/renesas/r8a779g0-sysc.c index a452709f066d..b932eba1b804 100644 --- a/drivers/soc/renesas/r8a779g0-sysc.c +++ b/drivers/soc/renesas/r8a779g0-sysc.c @@ -37,6 +37,7 @@ static struct rcar_gen4_sysc_area r8a779g0_areas[] __initdata = { { "a3vip0", R8A779G0_PD_A3VIP0, R8A779G0_PD_ALWAYS_ON }, { "a3vip1", R8A779G0_PD_A3VIP1, R8A779G0_PD_ALWAYS_ON }, { "a3vip2", R8A779G0_PD_A3VIP2, R8A779G0_PD_ALWAYS_ON }, + { "a3dul", R8A779G0_PD_A3DUL, R8A779G0_PD_ALWAYS_ON }, { "a3isp0", R8A779G0_PD_A3ISP0, R8A779G0_PD_ALWAYS_ON }, { "a3isp1", R8A779G0_PD_A3ISP1, R8A779G0_PD_ALWAYS_ON }, { "a3ir", R8A779G0_PD_A3IR, R8A779G0_PD_ALWAYS_ON }, |