Эх сурвалжийг харах

dm: power: domain: add BCM6328 power domain driver

This allows controlling MISC IDDQ register on BCM6328 SoCs.

Signed-off-by: Álvaro Fernández Rojas <noltari@gmail.com>
Álvaro Fernández Rojas 8 жил өмнө
parent
commit
7810fb9547

+ 7 - 0
drivers/power/domain/Kconfig

@@ -9,6 +9,13 @@ config POWER_DOMAIN
 	  domains). This may be used to save power. This API provides the
 	  domains). This may be used to save power. This API provides the
 	  means to control such power management hardware.
 	  means to control such power management hardware.
 
 
+config BCM6328_POWER_DOMAIN
+	bool "Enable the BCM6328 power domain driver"
+	depends on POWER_DOMAIN && ARCH_BMIPS
+	help
+	  Enable support for manipulating BCM6345 power domains via MMIO
+	  mapped registers.
+
 config SANDBOX_POWER_DOMAIN
 config SANDBOX_POWER_DOMAIN
 	bool "Enable the sandbox power domain test driver"
 	bool "Enable the sandbox power domain test driver"
 	depends on POWER_DOMAIN && SANDBOX
 	depends on POWER_DOMAIN && SANDBOX

+ 1 - 0
drivers/power/domain/Makefile

@@ -3,6 +3,7 @@
 # SPDX-License-Identifier: GPL-2.0
 # SPDX-License-Identifier: GPL-2.0
 
 
 obj-$(CONFIG_POWER_DOMAIN) += power-domain-uclass.o
 obj-$(CONFIG_POWER_DOMAIN) += power-domain-uclass.o
+obj-$(CONFIG_BCM6328_POWER_DOMAIN) += bcm6328-power-domain.o
 obj-$(CONFIG_SANDBOX_POWER_DOMAIN) += sandbox-power-domain.o
 obj-$(CONFIG_SANDBOX_POWER_DOMAIN) += sandbox-power-domain.o
 obj-$(CONFIG_SANDBOX_POWER_DOMAIN) += sandbox-power-domain-test.o
 obj-$(CONFIG_SANDBOX_POWER_DOMAIN) += sandbox-power-domain-test.o
 obj-$(CONFIG_TEGRA186_POWER_DOMAIN) += tegra186-power-domain.o
 obj-$(CONFIG_TEGRA186_POWER_DOMAIN) += tegra186-power-domain.o

+ 83 - 0
drivers/power/domain/bcm6328-power-domain.c

@@ -0,0 +1,83 @@
+/*
+ * Copyright (C) 2017 Álvaro Fernández Rojas <noltari@gmail.com>
+ *
+ * SPDX-License-Identifier: GPL-2.0+
+ */
+
+#include <common.h>
+#include <dm.h>
+#include <power-domain-uclass.h>
+#include <asm/io.h>
+
+#define MAX_DOMAINS	32
+
+struct bcm6328_power_domain {
+	void __iomem *regs;
+};
+
+static int bcm6328_power_domain_request(struct power_domain *power_domain)
+{
+	if (power_domain->id >= MAX_DOMAINS)
+		return -EINVAL;
+
+	return 0;
+}
+
+static int bcm6328_power_domain_free(struct power_domain *power_domain)
+{
+	return 0;
+}
+
+static int bcm6328_power_domain_on(struct power_domain *power_domain)
+{
+	struct bcm6328_power_domain *priv = dev_get_priv(power_domain->dev);
+
+	clrbits_be32(priv->regs, BIT(power_domain->id));
+
+	return 0;
+}
+
+static int bcm6328_power_domain_off(struct power_domain *power_domain)
+{
+	struct bcm6328_power_domain *priv = dev_get_priv(power_domain->dev);
+
+	setbits_be32(priv->regs, BIT(power_domain->id));
+
+	return 0;
+}
+
+static int bcm6328_power_domain_probe(struct udevice *dev)
+{
+	struct bcm6328_power_domain *priv = dev_get_priv(dev);
+	fdt_addr_t addr;
+	fdt_size_t size;
+
+	addr = dev_get_addr_size_index(dev, 0, &size);
+	if (addr == FDT_ADDR_T_NONE)
+		return -EINVAL;
+
+	priv->regs = ioremap(addr, size);
+
+	return 0;
+}
+
+static const struct udevice_id bcm6328_power_domain_ids[] = {
+	{ .compatible = "brcm,bcm6328-power-domain" },
+	{ /* sentinel */ }
+};
+
+struct power_domain_ops bcm6328_power_domain_ops = {
+	.free = bcm6328_power_domain_free,
+	.off = bcm6328_power_domain_off,
+	.on = bcm6328_power_domain_on,
+	.request = bcm6328_power_domain_request,
+};
+
+U_BOOT_DRIVER(bcm6328_power_domain) = {
+	.name = "bcm6328_power_domain",
+	.id = UCLASS_POWER_DOMAIN,
+	.of_match = bcm6328_power_domain_ids,
+	.ops = &bcm6328_power_domain_ops,
+	.priv_auto_alloc_size = sizeof(struct bcm6328_power_domain),
+	.probe = bcm6328_power_domain_probe,
+};