reset: ast2700: add reset driver support

Add reset controller driver for the dual-die AST2700 SoC. The
controller manages module-level reset signals via the modrst
register block at offset 0x200 within each SCU.

Signed-off-by: Ryan Chen <ryan_chen@aspeedtech.com>
This commit is contained in:
Ryan Chen
2026-06-29 13:43:20 -06:00
committed by Tom Rini
parent 0758fddb37
commit 6fb40812dd
4 changed files with 93 additions and 1 deletions
+1 -1
View File
@@ -222,7 +222,7 @@ F: drivers/net/ftgmac100.[ch]
F: drivers/pinctrl/aspeed/
F: drivers/pwm/pwm-aspeed.c
F: drivers/ram/aspeed/
F: drivers/reset/reset-ast2500.c
F: drivers/reset/reset-ast*.c
F: drivers/watchdog/ast_wdt.c
N: aspeed
N: ast2700
+9
View File
@@ -107,6 +107,15 @@ config RESET_AST2600
Say Y if you want to control reset signals of different peripherals
through System Control Unit (SCU).
config RESET_AST2700
bool "Reset controller driver for AST2700 SoCs"
depends on DM_RESET && ASPEED_AST2700
default y if ASPEED_AST2700
help
Support for reset controller on AST2700 SoC.
Say Y if you want to control reset signals of different peripherals
through System Control Unit (SCU).
config RESET_ROCKCHIP
bool "Reset controller driver for Rockchip SoCs"
depends on DM_RESET && ARCH_ROCKCHIP && CLK
+1
View File
@@ -18,6 +18,7 @@ obj-$(CONFIG_RESET_BRCMSTB_RESCAL) += reset-brcmstb-rescal.o
obj-$(CONFIG_RESET_UNIPHIER) += reset-uniphier.o
obj-$(CONFIG_RESET_AST2500) += reset-ast2500.o
obj-$(CONFIG_RESET_AST2600) += reset-ast2600.o
obj-$(CONFIG_RESET_AST2700) += reset-ast2700.o
obj-$(CONFIG_$(PHASE_)RESET_ROCKCHIP) += reset-rockchip.o rst-rk3506.o rst-rk3528.o rst-rk3576.o rst-rk3588.o
obj-$(CONFIG_RESET_MESON) += reset-meson.o
obj-$(CONFIG_RESET_SOCFPGA) += reset-socfpga.o
+82
View File
@@ -0,0 +1,82 @@
// SPDX-License-Identifier: GPL-2.0
/*
* Copyright (C) ASPEED Technology Inc.
*/
#include <asm/io.h>
#include <dm.h>
#include <linux/err.h>
#include <reset.h>
#include <reset-uclass.h>
/* Offset of the modrst register block within the SCU. */
#define AST2700_RESET_OFFSET 0x200
struct ast2700_reset_priv {
void __iomem *base;
};
static int ast2700_reset_assert(struct reset_ctl *reset_ctl)
{
struct ast2700_reset_priv *priv = dev_get_priv(reset_ctl->dev);
if (reset_ctl->id < 32)
writel(BIT(reset_ctl->id), priv->base);
else
writel(BIT(reset_ctl->id - 32), priv->base + 0x20);
return 0;
}
static int ast2700_reset_deassert(struct reset_ctl *reset_ctl)
{
struct ast2700_reset_priv *priv = dev_get_priv(reset_ctl->dev);
if (reset_ctl->id < 32)
writel(BIT(reset_ctl->id), priv->base + 0x04);
else
writel(BIT(reset_ctl->id - 32), priv->base + 0x24);
return 0;
}
static int ast2700_reset_status(struct reset_ctl *reset_ctl)
{
struct ast2700_reset_priv *priv = dev_get_priv(reset_ctl->dev);
int status;
if (reset_ctl->id < 32)
status = BIT(reset_ctl->id) & readl(priv->base);
else
status = BIT(reset_ctl->id - 32) & readl(priv->base + 0x20);
return !!status;
}
static int ast2700_reset_probe(struct udevice *dev)
{
struct ast2700_reset_priv *priv = dev_get_priv(dev);
void __iomem *scu_base;
scu_base = dev_read_addr_ptr(dev);
if (!scu_base)
return -EINVAL;
priv->base = scu_base + AST2700_RESET_OFFSET;
return 0;
}
static const struct reset_ops ast2700_reset_ops = {
.rst_assert = ast2700_reset_assert,
.rst_deassert = ast2700_reset_deassert,
.rst_status = ast2700_reset_status,
};
U_BOOT_DRIVER(ast2700_reset) = {
.name = "ast2700_reset",
.id = UCLASS_RESET,
.probe = ast2700_reset_probe,
.ops = &ast2700_reset_ops,
.priv_auto = sizeof(struct ast2700_reset_priv),
};