mirror of
https://github.com/torvalds/linux.git
synced 2026-06-02 11:33:28 +02:00
Reset controller updates for v6.11
Move reset controller registration to the end in rzg2l-usbphy-ctrl, to simplify the probe error path, add a new i.MX8MP AudioMix reset driver, allow to build some drivers under COMPILE_TEST with fewer dependencies, and use the devm_clk_get_enabled convenience wrapper in meson-audio-arb. The latter causes a trivial merge conflict [1] withb99e9c0961("reset: meson-audio-arb: Convert to platform remove callback returning void") because I didn't manage to send that in last round. There is no overlap though. [1] https://lore.kernel.org/all/Znmufb9L78FCoSSS@sirena.org.uk/ -----BEGIN PGP SIGNATURE----- iI0EABYIADUWIQRRO6F6WdpH1R0vGibVhaclGDdiwAUCZnxCbxcccC56YWJlbEBw ZW5ndXRyb25peC5kZQAKCRDVhaclGDdiwCR+AP9OYKv3E0rPqYU2YscSHZCX6XKN EtNECWEteDD+RnYxtQEAoAAkd6v5yEiYz8EAb4FeW36SncwDHtANnskBmjIAGwk= =cVo+ -----END PGP SIGNATURE----- gpgsig -----BEGIN PGP SIGNATURE----- iQIzBAABCgAdFiEEiK/NIGsWEZVxh/FrYKtH/8kJUicFAmZ9eoUACgkQYKtH/8kJ UicO0xAA5FwScw615MH+vTaOo+buyFH4W70WFNNmKsHVeSzNkjymtcJdn8sGPwai WrpSCoFFK5gNBes7K6xqRsWqzR1QnZeKIHBSwkaUHYFUbm4xPtEPux/3Hr9no5Y5 mB3ZVFmB2UEr+0QzkXKavOXcCfOZgYmuFRqtgftZg4ogq9z6JYi84L4ffBcdbeJ+ yEpa5ZmJb8a7rS6zLbMiyoeNEyLYMzRezyFY9RRkH/UypUReQ0NnaN/xqT5syinu 0L9Rta/Hz8tDqQMqJon71j1vOQ83nH5llPH3W9m39SDFGtUIFo2ZmZfBWnkO0Pke b28+IUmu9nKNt5wc9b1FXi3e3Sv8latF3hsq4yCY1mzO81NnjTlj039gazOedZfR E6rQbzQCPMxctZclDqJv0Y+CPftYGdG/hlbvhVSJ0nm3SccfXRiIVee7wzULKQCU 5OIE9MrxszWPA26pw7aFOAZ2l26aJyZvvX9nJUu163I6wpCCVnjpHvXGCr9mmJG0 HctOZbPxRa1GlYGFqUHioYwDmct0PHcIQP9YQUxiPskqsxZwF/Zq7sVXxIkIe32D hRDJ53liOOSWg0tkLAkdSC68vur/BDzaPYH530/Se+XtfJJet0KjhMdevW3fruRf TKfZJ1bOxG2vK+73DnhWIt5wqWMYzGqZzURKW8FOwn//DYc5ClQ= =CZzr -----END PGP SIGNATURE----- Merge tag 'reset-for-v6.11' of git://git.pengutronix.de/pza/linux into soc/drivers Reset controller updates for v6.11 Move reset controller registration to the end in rzg2l-usbphy-ctrl, to simplify the probe error path, add a new i.MX8MP AudioMix reset driver, allow to build some drivers under COMPILE_TEST with fewer dependencies, and use the devm_clk_get_enabled convenience wrapper in meson-audio-arb. The latter causes a trivial merge conflict [1] withb99e9c0961("reset: meson-audio-arb: Convert to platform remove callback returning void") because I didn't manage to send that in last round. There is no overlap though. [1] https://lore.kernel.org/all/Znmufb9L78FCoSSS@sirena.org.uk/ * tag 'reset-for-v6.11' of git://git.pengutronix.de/pza/linux: reset: RESET_IMX8MP_AUDIOMIX should depend on ARCH_MXC reset: zynqmp: allow building under COMPILE_TEST reset: imx8mp-audiomix: Add AudioMix Block Control reset driver reset: meson-audio-arb: Use devm_clk_get_enabled() reset: sti: allow building under COMPILE_TEST reset: rzg2l-usbphy-ctrl: Move reset controller registration Link: https://lore.kernel.org/r/20240626163258.61222-1-p.zabel@pengutronix.de Signed-off-by: Arnd Bergmann <arnd@arndb.de>
This commit is contained in:
commit
f42af02c0a
|
|
@ -91,6 +91,14 @@ config RESET_IMX7
|
|||
help
|
||||
This enables the reset controller driver for i.MX7 SoCs.
|
||||
|
||||
config RESET_IMX8MP_AUDIOMIX
|
||||
tristate "i.MX8MP AudioMix Reset Driver"
|
||||
depends on ARCH_MXC || COMPILE_TEST
|
||||
select AUXILIARY_BUS
|
||||
default CLK_IMX8MP
|
||||
help
|
||||
This enables the reset controller driver for i.MX8MP AudioMix
|
||||
|
||||
config RESET_INTEL_GW
|
||||
bool "Intel Reset Controller Driver"
|
||||
depends on X86 || COMPILE_TEST
|
||||
|
|
@ -328,6 +336,12 @@ config RESET_ZYNQ
|
|||
help
|
||||
This enables the reset controller driver for Xilinx Zynq SoCs.
|
||||
|
||||
config RESET_ZYNQMP
|
||||
bool "ZYNQMP Reset Driver" if COMPILE_TEST
|
||||
default ARCH_ZYNQMP
|
||||
help
|
||||
This enables the reset controller driver for Xilinx ZynqMP SoCs.
|
||||
|
||||
source "drivers/reset/starfive/Kconfig"
|
||||
source "drivers/reset/sti/Kconfig"
|
||||
source "drivers/reset/hisilicon/Kconfig"
|
||||
|
|
|
|||
|
|
@ -2,7 +2,7 @@
|
|||
obj-y += core.o
|
||||
obj-y += hisilicon/
|
||||
obj-y += starfive/
|
||||
obj-$(CONFIG_ARCH_STI) += sti/
|
||||
obj-y += sti/
|
||||
obj-$(CONFIG_ARCH_TEGRA) += tegra/
|
||||
obj-$(CONFIG_RESET_A10SR) += reset-a10sr.o
|
||||
obj-$(CONFIG_RESET_ATH79) += reset-ath79.o
|
||||
|
|
@ -14,6 +14,7 @@ obj-$(CONFIG_RESET_BRCMSTB_RESCAL) += reset-brcmstb-rescal.o
|
|||
obj-$(CONFIG_RESET_GPIO) += reset-gpio.o
|
||||
obj-$(CONFIG_RESET_HSDK) += reset-hsdk.o
|
||||
obj-$(CONFIG_RESET_IMX7) += reset-imx7.o
|
||||
obj-$(CONFIG_RESET_IMX8MP_AUDIOMIX) += reset-imx8mp-audiomix.o
|
||||
obj-$(CONFIG_RESET_INTEL_GW) += reset-intel-gw.o
|
||||
obj-$(CONFIG_RESET_K210) += reset-k210.o
|
||||
obj-$(CONFIG_RESET_LANTIQ) += reset-lantiq.o
|
||||
|
|
@ -41,4 +42,4 @@ obj-$(CONFIG_RESET_TN48M_CPLD) += reset-tn48m.o
|
|||
obj-$(CONFIG_RESET_UNIPHIER) += reset-uniphier.o
|
||||
obj-$(CONFIG_RESET_UNIPHIER_GLUE) += reset-uniphier-glue.o
|
||||
obj-$(CONFIG_RESET_ZYNQ) += reset-zynq.o
|
||||
obj-$(CONFIG_ARCH_ZYNQMP) += reset-zynqmp.o
|
||||
obj-$(CONFIG_RESET_ZYNQMP) += reset-zynqmp.o
|
||||
|
|
|
|||
128
drivers/reset/reset-imx8mp-audiomix.c
Normal file
128
drivers/reset/reset-imx8mp-audiomix.c
Normal file
|
|
@ -0,0 +1,128 @@
|
|||
// SPDX-License-Identifier: GPL-2.0-or-later
|
||||
/*
|
||||
* Copyright 2024 NXP
|
||||
*/
|
||||
|
||||
#include <linux/auxiliary_bus.h>
|
||||
#include <linux/device.h>
|
||||
#include <linux/io.h>
|
||||
#include <linux/module.h>
|
||||
#include <linux/of.h>
|
||||
#include <linux/of_address.h>
|
||||
#include <linux/reset-controller.h>
|
||||
|
||||
#define EARC 0x200
|
||||
#define EARC_RESET_MASK 0x3
|
||||
|
||||
struct imx8mp_audiomix_reset {
|
||||
struct reset_controller_dev rcdev;
|
||||
spinlock_t lock; /* protect register read-modify-write cycle */
|
||||
void __iomem *base;
|
||||
};
|
||||
|
||||
static struct imx8mp_audiomix_reset *to_imx8mp_audiomix_reset(struct reset_controller_dev *rcdev)
|
||||
{
|
||||
return container_of(rcdev, struct imx8mp_audiomix_reset, rcdev);
|
||||
}
|
||||
|
||||
static int imx8mp_audiomix_reset_assert(struct reset_controller_dev *rcdev,
|
||||
unsigned long id)
|
||||
{
|
||||
struct imx8mp_audiomix_reset *priv = to_imx8mp_audiomix_reset(rcdev);
|
||||
void __iomem *reg_addr = priv->base;
|
||||
unsigned int mask, reg;
|
||||
unsigned long flags;
|
||||
|
||||
mask = BIT(id);
|
||||
spin_lock_irqsave(&priv->lock, flags);
|
||||
reg = readl(reg_addr + EARC);
|
||||
writel(reg & ~mask, reg_addr + EARC);
|
||||
spin_unlock_irqrestore(&priv->lock, flags);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int imx8mp_audiomix_reset_deassert(struct reset_controller_dev *rcdev,
|
||||
unsigned long id)
|
||||
{
|
||||
struct imx8mp_audiomix_reset *priv = to_imx8mp_audiomix_reset(rcdev);
|
||||
void __iomem *reg_addr = priv->base;
|
||||
unsigned int mask, reg;
|
||||
unsigned long flags;
|
||||
|
||||
mask = BIT(id);
|
||||
spin_lock_irqsave(&priv->lock, flags);
|
||||
reg = readl(reg_addr + EARC);
|
||||
writel(reg | mask, reg_addr + EARC);
|
||||
spin_unlock_irqrestore(&priv->lock, flags);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static const struct reset_control_ops imx8mp_audiomix_reset_ops = {
|
||||
.assert = imx8mp_audiomix_reset_assert,
|
||||
.deassert = imx8mp_audiomix_reset_deassert,
|
||||
};
|
||||
|
||||
static int imx8mp_audiomix_reset_probe(struct auxiliary_device *adev,
|
||||
const struct auxiliary_device_id *id)
|
||||
{
|
||||
struct imx8mp_audiomix_reset *priv;
|
||||
struct device *dev = &adev->dev;
|
||||
int ret;
|
||||
|
||||
priv = devm_kzalloc(dev, sizeof(*priv), GFP_KERNEL);
|
||||
if (!priv)
|
||||
return -ENOMEM;
|
||||
|
||||
spin_lock_init(&priv->lock);
|
||||
|
||||
priv->rcdev.owner = THIS_MODULE;
|
||||
priv->rcdev.nr_resets = fls(EARC_RESET_MASK);
|
||||
priv->rcdev.ops = &imx8mp_audiomix_reset_ops;
|
||||
priv->rcdev.of_node = dev->parent->of_node;
|
||||
priv->rcdev.dev = dev;
|
||||
priv->rcdev.of_reset_n_cells = 1;
|
||||
priv->base = of_iomap(dev->parent->of_node, 0);
|
||||
if (!priv->base)
|
||||
return -ENOMEM;
|
||||
|
||||
dev_set_drvdata(dev, priv);
|
||||
|
||||
ret = devm_reset_controller_register(dev, &priv->rcdev);
|
||||
if (ret)
|
||||
goto out_unmap;
|
||||
|
||||
return 0;
|
||||
|
||||
out_unmap:
|
||||
iounmap(priv->base);
|
||||
return ret;
|
||||
}
|
||||
|
||||
static void imx8mp_audiomix_reset_remove(struct auxiliary_device *adev)
|
||||
{
|
||||
struct imx8mp_audiomix_reset *priv = dev_get_drvdata(&adev->dev);
|
||||
|
||||
iounmap(priv->base);
|
||||
}
|
||||
|
||||
static const struct auxiliary_device_id imx8mp_audiomix_reset_ids[] = {
|
||||
{
|
||||
.name = "clk_imx8mp_audiomix.reset",
|
||||
},
|
||||
{ }
|
||||
};
|
||||
MODULE_DEVICE_TABLE(auxiliary, imx8mp_audiomix_reset_ids);
|
||||
|
||||
static struct auxiliary_driver imx8mp_audiomix_reset_driver = {
|
||||
.probe = imx8mp_audiomix_reset_probe,
|
||||
.remove = imx8mp_audiomix_reset_remove,
|
||||
.id_table = imx8mp_audiomix_reset_ids,
|
||||
};
|
||||
|
||||
module_auxiliary_driver(imx8mp_audiomix_reset_driver);
|
||||
|
||||
MODULE_AUTHOR("Shengjiu Wang <shengjiu.wang@nxp.com>");
|
||||
MODULE_DESCRIPTION("Freescale i.MX8MP Audio Block Controller reset driver");
|
||||
MODULE_LICENSE("GPL");
|
||||
|
|
@ -129,8 +129,6 @@ static int meson_audio_arb_remove(struct platform_device *pdev)
|
|||
writel(0, arb->regs);
|
||||
spin_unlock(&arb->lock);
|
||||
|
||||
clk_disable_unprepare(arb->clk);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
|
@ -150,7 +148,7 @@ static int meson_audio_arb_probe(struct platform_device *pdev)
|
|||
return -ENOMEM;
|
||||
platform_set_drvdata(pdev, arb);
|
||||
|
||||
arb->clk = devm_clk_get(dev, NULL);
|
||||
arb->clk = devm_clk_get_enabled(dev, NULL);
|
||||
if (IS_ERR(arb->clk))
|
||||
return dev_err_probe(dev, PTR_ERR(arb->clk), "failed to get clock\n");
|
||||
|
||||
|
|
@ -170,11 +168,6 @@ static int meson_audio_arb_probe(struct platform_device *pdev)
|
|||
* In the initial state, all memory interfaces are disabled
|
||||
* and the general bit is on
|
||||
*/
|
||||
ret = clk_prepare_enable(arb->clk);
|
||||
if (ret) {
|
||||
dev_err(dev, "failed to enable arb clock\n");
|
||||
return ret;
|
||||
}
|
||||
writel(BIT(ARB_GENERAL_BIT), arb->regs);
|
||||
|
||||
/* Register reset controller */
|
||||
|
|
|
|||
|
|
@ -125,25 +125,14 @@ static int rzg2l_usbphy_ctrl_probe(struct platform_device *pdev)
|
|||
if (error)
|
||||
return error;
|
||||
|
||||
priv->rcdev.ops = &rzg2l_usbphy_ctrl_reset_ops;
|
||||
priv->rcdev.of_reset_n_cells = 1;
|
||||
priv->rcdev.nr_resets = NUM_PORTS;
|
||||
priv->rcdev.of_node = dev->of_node;
|
||||
priv->rcdev.dev = dev;
|
||||
|
||||
error = devm_reset_controller_register(dev, &priv->rcdev);
|
||||
if (error)
|
||||
return error;
|
||||
|
||||
spin_lock_init(&priv->lock);
|
||||
dev_set_drvdata(dev, priv);
|
||||
|
||||
pm_runtime_enable(&pdev->dev);
|
||||
error = pm_runtime_resume_and_get(&pdev->dev);
|
||||
if (error < 0) {
|
||||
pm_runtime_disable(&pdev->dev);
|
||||
reset_control_assert(priv->rstc);
|
||||
return dev_err_probe(&pdev->dev, error, "pm_runtime_resume_and_get failed");
|
||||
dev_err_probe(&pdev->dev, error, "pm_runtime_resume_and_get failed");
|
||||
goto err_pm_disable_reset_deassert;
|
||||
}
|
||||
|
||||
/* put pll and phy into reset state */
|
||||
|
|
@ -153,7 +142,24 @@ static int rzg2l_usbphy_ctrl_probe(struct platform_device *pdev)
|
|||
writel(val, priv->base + RESET);
|
||||
spin_unlock_irqrestore(&priv->lock, flags);
|
||||
|
||||
priv->rcdev.ops = &rzg2l_usbphy_ctrl_reset_ops;
|
||||
priv->rcdev.of_reset_n_cells = 1;
|
||||
priv->rcdev.nr_resets = NUM_PORTS;
|
||||
priv->rcdev.of_node = dev->of_node;
|
||||
priv->rcdev.dev = dev;
|
||||
|
||||
error = devm_reset_controller_register(dev, &priv->rcdev);
|
||||
if (error)
|
||||
goto err_pm_runtime_put;
|
||||
|
||||
return 0;
|
||||
|
||||
err_pm_runtime_put:
|
||||
pm_runtime_put(&pdev->dev);
|
||||
err_pm_disable_reset_deassert:
|
||||
pm_runtime_disable(&pdev->dev);
|
||||
reset_control_assert(priv->rstc);
|
||||
return error;
|
||||
}
|
||||
|
||||
static int rzg2l_usbphy_ctrl_remove(struct platform_device *pdev)
|
||||
|
|
|
|||
|
|
@ -1,7 +1,7 @@
|
|||
# SPDX-License-Identifier: GPL-2.0-only
|
||||
if ARCH_STI
|
||||
if ARCH_STI || COMPILE_TEST
|
||||
|
||||
config STIH407_RESET
|
||||
bool
|
||||
bool "STIH407 Reset Driver" if COMPILE_TEST
|
||||
|
||||
endif
|
||||
|
|
|
|||
Loading…
Reference in New Issue
Block a user