From 758de97bb8be091e0b1ab25af6bb9965d54fa839 Mon Sep 17 00:00:00 2001 From: Michal Simek Date: Thu, 12 Jul 2018 10:36:07 +0200 Subject: sysreset: dm: Support manual relocation for sysreset Relocate sysreset ops as was done by: "dm: Add support for all targets which requires MANUAL_RELOC" (sha1: 484fdf5ba058b07be5ca82763aa2b72063540ef3) Signed-off-by: Michal Simek Reviewed-by: Simon Glass --- drivers/sysreset/sysreset-uclass.c | 16 ++++++++++++++++ 1 file changed, 16 insertions(+) (limited to 'drivers/sysreset') diff --git a/drivers/sysreset/sysreset-uclass.c b/drivers/sysreset/sysreset-uclass.c index 7e06c3c90a7..840eab6b570 100644 --- a/drivers/sysreset/sysreset-uclass.c +++ b/drivers/sysreset/sysreset-uclass.c @@ -74,7 +74,23 @@ int do_reset(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[]) return 0; } +static int sysreset_post_bind(struct udevice *dev) +{ +#if defined(CONFIG_NEEDS_MANUAL_RELOC) + struct sysreset_ops *ops = sysreset_get_ops(dev); + static int reloc_done; + + if (!reloc_done) { + if (ops->request) + ops->request += gd->reloc_off; + reloc_done++; + } +#endif + return 0; +} + UCLASS_DRIVER(sysreset) = { .id = UCLASS_SYSRESET, .name = "sysreset", + .post_bind = sysreset_post_bind, }; -- cgit v1.3.1 From 0d832b322109e76953bc58e4d2723d2c73dfb604 Mon Sep 17 00:00:00 2001 From: Michal Simek Date: Fri, 13 Jul 2018 11:04:56 +0200 Subject: sysreset: Add support for gpio-restart The Linux kernel has binding for gpio-restart node. This patch is adding basic support without supporting any optional properties. This driver was tested on Microblaze system where gpio is connected to SoC reset logic. Output value is handled via gpios cells values. In gpio_reboot_request() set_value is writing 1 because dm_gpio_set_value() is capable to changing it when it is ACTIVE_LOW. ... if (desc->flags & GPIOD_ACTIVE_LOW) value = !value; ... Signed-off-by: Michal Simek Reviewed-by: Philipp Tomsich Reviewed-by: Simon Glass --- MAINTAINERS | 1 + drivers/sysreset/Kconfig | 8 ++++++ drivers/sysreset/Makefile | 1 + drivers/sysreset/sysreset_gpio.c | 59 ++++++++++++++++++++++++++++++++++++++++ 4 files changed, 69 insertions(+) create mode 100644 drivers/sysreset/sysreset_gpio.c (limited to 'drivers/sysreset') diff --git a/MAINTAINERS b/MAINTAINERS index 570bc6d1a52..91e4ad7c75a 100644 --- a/MAINTAINERS +++ b/MAINTAINERS @@ -419,6 +419,7 @@ F: drivers/net/xilinx_axi_emac.c F: drivers/net/xilinx_emaclite.c F: drivers/serial/serial_xuartlite.c F: drivers/spi/xilinx_spi.c +F: drivers/sysreset/sysreset_gpio.c F: drivers/watchdog/xilinx_tb_wdt.c N: xilinx diff --git a/drivers/sysreset/Kconfig b/drivers/sysreset/Kconfig index a6d48e8a662..cec612ed50d 100644 --- a/drivers/sysreset/Kconfig +++ b/drivers/sysreset/Kconfig @@ -15,6 +15,14 @@ config SYSRESET if SYSRESET +config SYSRESET_GPIO + bool "Enable support for GPIO reset driver" + select GPIO + help + Reset support via GPIO pin connected reset logic. This is used for + example on Microblaze where reset logic can be controlled via GPIO + pin which triggers cpu reset. + config SYSRESET_PSCI bool "Enable support for PSCI System Reset" depends on ARM_PSCI_FW diff --git a/drivers/sysreset/Makefile b/drivers/sysreset/Makefile index 0da58a1cf6a..ca533cfefaa 100644 --- a/drivers/sysreset/Makefile +++ b/drivers/sysreset/Makefile @@ -3,6 +3,7 @@ # (C) Copyright 2016 Cadence Design Systems Inc. obj-$(CONFIG_SYSRESET) += sysreset-uclass.o +obj-$(CONFIG_SYSRESET_GPIO) += sysreset_gpio.o obj-$(CONFIG_SYSRESET_PSCI) += sysreset_psci.o obj-$(CONFIG_SYSRESET_SYSCON) += sysreset_syscon.o obj-$(CONFIG_SYSRESET_WATCHDOG) += sysreset_watchdog.o diff --git a/drivers/sysreset/sysreset_gpio.c b/drivers/sysreset/sysreset_gpio.c new file mode 100644 index 00000000000..ed9a49ad08c --- /dev/null +++ b/drivers/sysreset/sysreset_gpio.c @@ -0,0 +1,59 @@ +// SPDX-License-Identifier: GPL-2.0 +/* + * Copyright (C) 2018 Xilinx, Inc. - Michal Simek + */ + +#include +#include +#include +#include +#include + +struct gpio_reboot_priv { + struct gpio_desc gpio; +}; + +static int gpio_reboot_request(struct udevice *dev, enum sysreset_t type) +{ + struct gpio_reboot_priv *priv = dev_get_priv(dev); + + /* + * When debug log is enabled please make sure that chars won't end up + * in output fifo. Or you can append udelay(); to get enough time + * to HW to emit output fifo. + */ + debug("GPIO reset\n"); + + /* Writing 1 respects polarity (active high/low) based on gpio->flags */ + return dm_gpio_set_value(&priv->gpio, 1); +} + +static struct sysreset_ops gpio_reboot_ops = { + .request = gpio_reboot_request, +}; + +int gpio_reboot_probe(struct udevice *dev) +{ + struct gpio_reboot_priv *priv = dev_get_priv(dev); + + /* + * Linux kernel DT binding contain others optional properties + * which are not supported now + */ + + return gpio_request_by_name(dev, "gpios", 0, &priv->gpio, GPIOD_IS_OUT); +} + +static const struct udevice_id led_gpio_ids[] = { + { .compatible = "gpio-restart" }, + { } +}; + +U_BOOT_DRIVER(gpio_reboot) = { + .id = UCLASS_SYSRESET, + .name = "gpio_restart", + .of_match = led_gpio_ids, + .ops = &gpio_reboot_ops, + .priv_auto_alloc_size = sizeof(struct gpio_reboot_priv), + .probe = gpio_reboot_probe, +}; -- cgit v1.3.1 From cae39ae365ed98b7cd0805fcb57ca4ee280b5ebe Mon Sep 17 00:00:00 2001 From: Michal Simek Date: Fri, 13 Jul 2018 17:00:13 +0200 Subject: sysreset: Add support for Microblaze soft reset jump Microblaze is storing reset vector at address 0x0. It means soft reset can be done by just jumping to this address. This code was in platform code but sysreset interface is providing enough capabilities to have more options how to reset the system. It can go from gpio reset through watchdog reset till soft reset. The driver has not compatible string because this is cpu specific and DM core is not able to detect compatible string in DT root that's why this driver will be instantiated from platform code by calling device_bind_driver(gd->dm_root, "mb_soft_reset", "reset_soft", NULL); It should be bind as the last reset method to ensure that hw reset is called before this. Signed-off-by: Michal Simek --- drivers/sysreset/Kconfig | 6 ++++++ drivers/sysreset/Makefile | 1 + drivers/sysreset/sysreset_microblaze.c | 30 ++++++++++++++++++++++++++++++ 3 files changed, 37 insertions(+) create mode 100644 drivers/sysreset/sysreset_microblaze.c (limited to 'drivers/sysreset') diff --git a/drivers/sysreset/Kconfig b/drivers/sysreset/Kconfig index cec612ed50d..f2524c18b7b 100644 --- a/drivers/sysreset/Kconfig +++ b/drivers/sysreset/Kconfig @@ -23,6 +23,12 @@ config SYSRESET_GPIO example on Microblaze where reset logic can be controlled via GPIO pin which triggers cpu reset. +config SYSRESET_MICROBLAZE + bool "Enable support for Microblaze soft reset" + depends on MICROBLAZE + help + This is soft reset on Microblaze which does jump to 0x0 address. + config SYSRESET_PSCI bool "Enable support for PSCI System Reset" depends on ARM_PSCI_FW diff --git a/drivers/sysreset/Makefile b/drivers/sysreset/Makefile index ca533cfefaa..223a0716f0a 100644 --- a/drivers/sysreset/Makefile +++ b/drivers/sysreset/Makefile @@ -4,6 +4,7 @@ obj-$(CONFIG_SYSRESET) += sysreset-uclass.o obj-$(CONFIG_SYSRESET_GPIO) += sysreset_gpio.o +obj-$(CONFIG_SYSRESET_MICROBLAZE) += sysreset_microblaze.o obj-$(CONFIG_SYSRESET_PSCI) += sysreset_psci.o obj-$(CONFIG_SYSRESET_SYSCON) += sysreset_syscon.o obj-$(CONFIG_SYSRESET_WATCHDOG) += sysreset_watchdog.o diff --git a/drivers/sysreset/sysreset_microblaze.c b/drivers/sysreset/sysreset_microblaze.c new file mode 100644 index 00000000000..514c95817f2 --- /dev/null +++ b/drivers/sysreset/sysreset_microblaze.c @@ -0,0 +1,30 @@ +// SPDX-License-Identifier: GPL-2.0 +/* + * Copyright (C) 2018 Xilinx, Inc. - Michal Simek + */ + +#include +#include +#include +#include +#include + +static int microblaze_sysreset_request(struct udevice *dev, + enum sysreset_t type) +{ + puts("Microblaze soft reset sysreset\n"); + __asm__ __volatile__ (" mts rmsr, r0;" \ + "bra r0"); + + return -EINPROGRESS; +} + +static struct sysreset_ops microblaze_sysreset = { + .request = microblaze_sysreset_request, +}; + +U_BOOT_DRIVER(sysreset_microblaze) = { + .id = UCLASS_SYSRESET, + .name = "mb_soft_reset", + .ops = µblaze_sysreset, +}; -- cgit v1.3.1