* [PATCH 0/8] ARM: i.MX7: add serial download reboot mode
@ 2022-10-17 7:09 Ahmad Fatoum
2022-10-17 7:09 ` [PATCH 1/8] restart: make restart.h header self-contained Ahmad Fatoum
` (8 more replies)
0 siblings, 9 replies; 10+ messages in thread
From: Ahmad Fatoum @ 2022-10-17 7:09 UTC (permalink / raw)
To: barebox
BootROM can be forced into USB recovery on i.MX7 just like on the
i.MX8M, with the difference that reset is a bit more involved,
because warm resets via watchdogs are broken on this SoC.
We do a bit of cleanup and then tackle that via a syscon-reboot
device describing the Cortex-A7 CPU0 reset.
Ahmad Fatoum (8):
restart: make restart.h header self-contained
restart: do restart-priority OF parsing in restart_handler_register
restart: add reset -w for warm bootrom reset
watchdog: imxwd: don't register broken imxwd-warm for i.MX7
watchdog: imxwd: set imxwd-warm as reboot mode default handler
Documentations: devicetree: bindings: document watchdog-priority
ARM: i.MX7: describe USB serial download boot mode
ARM: stm32mp: mark iwdg2 with barebox,restart-warm-bootrom
Documentation/boards/imx.rst | 2 +-
Documentation/boards/stm32mp.rst | 6 ++-
.../devicetree/bindings/power/restart.rst | 15 ++++++++
.../devicetree/bindings/watchdog/watchdog.rst | 10 +++++
Documentation/user/reboot-mode.rst | 7 +++-
arch/arm/configs/imx_v7_defconfig | 2 +
arch/arm/dts/imx7.dtsi | 37 +++++++++++++++++++
arch/arm/dts/stm32mp131.dtsi | 4 ++
arch/arm/dts/stm32mp151.dtsi | 4 ++
commands/reset.c | 16 +++++---
common/restart.c | 37 +++++++++----------
drivers/clk/clk-stm32mp1.c | 2 +-
drivers/mfd/da9053.c | 2 +-
drivers/mfd/da9063.c | 2 +-
drivers/mfd/rn5t568.c | 2 +-
drivers/power/reset/stm32-reboot.c | 6 ++-
drivers/power/reset/syscon-reboot.c | 1 +
drivers/watchdog/imxwd.c | 31 ++++++++++++----
include/restart.h | 15 ++++++--
include/soc/stm32/reboot.h | 6 ++-
20 files changed, 161 insertions(+), 46 deletions(-)
create mode 100644 Documentation/devicetree/bindings/power/restart.rst
create mode 100644 Documentation/devicetree/bindings/watchdog/watchdog.rst
create mode 100644 arch/arm/dts/imx7.dtsi
--
2.30.2
^ permalink raw reply [flat|nested] 10+ messages in thread
* [PATCH 1/8] restart: make restart.h header self-contained
2022-10-17 7:09 [PATCH 0/8] ARM: i.MX7: add serial download reboot mode Ahmad Fatoum
@ 2022-10-17 7:09 ` Ahmad Fatoum
2022-10-17 7:09 ` [PATCH 2/8] restart: do restart-priority OF parsing in restart_handler_register Ahmad Fatoum
` (7 subsequent siblings)
8 siblings, 0 replies; 10+ messages in thread
From: Ahmad Fatoum @ 2022-10-17 7:09 UTC (permalink / raw)
To: barebox; +Cc: Ahmad Fatoum
Code may fail compile depending on include order. Fix this.
Signed-off-by: Ahmad Fatoum <a.fatoum@pengutronix.de>
---
include/restart.h | 5 +++++
1 file changed, 5 insertions(+)
diff --git a/include/restart.h b/include/restart.h
index 2d15c7598acc..27fab1b80dfb 100644
--- a/include/restart.h
+++ b/include/restart.h
@@ -2,6 +2,11 @@
#ifndef __INCLUDE_RESTART_H
#define __INCLUDE_RESTART_H
+#include <linux/compiler.h>
+#include <linux/types.h>
+
+struct device_node;
+
void restart_handlers_print(void);
void __noreturn restart_machine(void);
struct restart_handler *restart_handler_get_by_name(const char *name);
--
2.30.2
^ permalink raw reply [flat|nested] 10+ messages in thread
* [PATCH 2/8] restart: do restart-priority OF parsing in restart_handler_register
2022-10-17 7:09 [PATCH 0/8] ARM: i.MX7: add serial download reboot mode Ahmad Fatoum
2022-10-17 7:09 ` [PATCH 1/8] restart: make restart.h header self-contained Ahmad Fatoum
@ 2022-10-17 7:09 ` Ahmad Fatoum
2022-10-17 7:09 ` [PATCH 3/8] restart: add reset -w for warm bootrom reset Ahmad Fatoum
` (6 subsequent siblings)
8 siblings, 0 replies; 10+ messages in thread
From: Ahmad Fatoum @ 2022-10-17 7:09 UTC (permalink / raw)
To: barebox; +Cc: Ahmad Fatoum
The restart-priority OF property is parsed for a number of MFDs, but
there is no reason really not to parse it for every restart handler that
has a device tree node like we already do for watchdogs.
Add a new struct restart_handler::of_node field and look into it if
populated. With this of_get_restart_priority, is no longer used, so drop it.
Signed-off-by: Ahmad Fatoum <a.fatoum@pengutronix.de>
---
.../devicetree/bindings/power/restart.rst | 10 ++++++++++
common/restart.c | 20 +++++--------------
drivers/mfd/da9053.c | 2 +-
drivers/mfd/da9063.c | 2 +-
drivers/mfd/rn5t568.c | 2 +-
include/restart.h | 5 +++--
6 files changed, 21 insertions(+), 20 deletions(-)
create mode 100644 Documentation/devicetree/bindings/power/restart.rst
diff --git a/Documentation/devicetree/bindings/power/restart.rst b/Documentation/devicetree/bindings/power/restart.rst
new file mode 100644
index 000000000000..8c866f6e0ded
--- /dev/null
+++ b/Documentation/devicetree/bindings/power/restart.rst
@@ -0,0 +1,10 @@
+System Restart Controllers
+==========================
+
+In addition to upstream bindings, following properties are understood:
+
+Optional properties:
+
+- ``restart-priority`` : Overrides the priority set by the driver. Normally,
+ the device with the biggest reach should reset the system.
+ See :ref:`_system_reset` for more information.
diff --git a/common/restart.c b/common/restart.c
index b6f2bbf25b10..9e988838bc60 100644
--- a/common/restart.c
+++ b/common/restart.c
@@ -27,6 +27,11 @@ int restart_handler_register(struct restart_handler *rst)
if (!rst->priority)
rst->priority = RESTART_DEFAULT_PRIORITY;
+ if (rst->of_node) {
+ of_property_read_u32(rst->of_node, "restart-priority",
+ &rst->priority);
+ }
+
list_add_tail(&rst->list, &restart_handler_list);
pr_debug("registering restart handler \"%s\" with priority %d\n",
@@ -102,21 +107,6 @@ void __noreturn restart_machine(void)
hang();
}
-/**
- * of_get_restart_priority() - get the desired restart priority from device tree
- * @node: The device_node to read the property from
- *
- * return: The priority
- */
-unsigned int of_get_restart_priority(struct device_node *node)
-{
- unsigned int priority = RESTART_DEFAULT_PRIORITY;
-
- of_property_read_u32(node, "restart-priority", &priority);
-
- return priority;
-}
-
/*
* restart_handlers_print - print informations about all restart handlers
*/
diff --git a/drivers/mfd/da9053.c b/drivers/mfd/da9053.c
index 99827c968922..693c0ca606f7 100644
--- a/drivers/mfd/da9053.c
+++ b/drivers/mfd/da9053.c
@@ -272,7 +272,7 @@ static int da9053_probe(struct device_d *dev)
da9053_detect_reset_source(da9053);
- da9053->restart.priority = of_get_restart_priority(dev->device_node);
+ da9053->restart.of_node = dev->device_node;
da9053->restart.name = "da9063";
da9053->restart.restart = &da9053_force_system_reset;
diff --git a/drivers/mfd/da9063.c b/drivers/mfd/da9063.c
index a4e5226f3c98..4627dd1aa5a2 100644
--- a/drivers/mfd/da9063.c
+++ b/drivers/mfd/da9063.c
@@ -383,7 +383,7 @@ static int da9063_probe(struct device_d *dev)
da9063_detect_reset_source(priv);
- priv->restart.priority = of_get_restart_priority(dev->device_node);
+ priv->restart.of_node = dev->device_node;
priv->restart.name = "da9063";
priv->restart.restart = &da9063_restart;
diff --git a/drivers/mfd/rn5t568.c b/drivers/mfd/rn5t568.c
index c1c792cbecf0..4bbab54fe48b 100644
--- a/drivers/mfd/rn5t568.c
+++ b/drivers/mfd/rn5t568.c
@@ -138,7 +138,7 @@ static int __init rn5t568_i2c_probe(struct device_d *dev)
regmap_write(pmic_instance->regmap, RN5T568_REPCNT, RN5T568_REPCNT_OFF_RESETO_16MS |
RN5T568_REPCNT_OFF_REPWRTIM_1000MS | RN5T568_REPCNT_OFF_REPWRON);
- pmic_instance->restart.priority = of_get_restart_priority(dev->device_node);
+ pmic_instance->restart.of_node = dev->device_node;
pmic_instance->restart.name = "RN5T568";
pmic_instance->restart.restart = &rn5t568_restart;
restart_handler_register(&pmic_instance->restart);
diff --git a/include/restart.h b/include/restart.h
index 27fab1b80dfb..330b50a53ab2 100644
--- a/include/restart.h
+++ b/include/restart.h
@@ -11,9 +11,12 @@ void restart_handlers_print(void);
void __noreturn restart_machine(void);
struct restart_handler *restart_handler_get_by_name(const char *name);
+struct device_node;
+
struct restart_handler {
void (*restart)(struct restart_handler *);
int priority;
+ struct device_node *of_node;
const char *name;
struct list_head list;
};
@@ -24,6 +27,4 @@ int restart_handler_register_fn(const char *name,
#define RESTART_DEFAULT_PRIORITY 100
-unsigned int of_get_restart_priority(struct device_node *node);
-
#endif /* __INCLUDE_RESTART_H */
--
2.30.2
^ permalink raw reply [flat|nested] 10+ messages in thread
* [PATCH 3/8] restart: add reset -w for warm bootrom reset
2022-10-17 7:09 [PATCH 0/8] ARM: i.MX7: add serial download reboot mode Ahmad Fatoum
2022-10-17 7:09 ` [PATCH 1/8] restart: make restart.h header self-contained Ahmad Fatoum
2022-10-17 7:09 ` [PATCH 2/8] restart: do restart-priority OF parsing in restart_handler_register Ahmad Fatoum
@ 2022-10-17 7:09 ` Ahmad Fatoum
2022-10-17 7:09 ` [PATCH 4/8] watchdog: imxwd: don't register broken imxwd-warm for i.MX7 Ahmad Fatoum
` (5 subsequent siblings)
8 siblings, 0 replies; 10+ messages in thread
From: Ahmad Fatoum @ 2022-10-17 7:09 UTC (permalink / raw)
To: barebox; +Cc: Ahmad Fatoum
We currently support reboot mode communication with BootROMs of the
i.MX6Q/DL, i.MX8MM and STM32MP15x. For each of these, the user must
take care to use the correct reset as the highest priority reset often
clears the non-volatile register mapped by the syscon holding the reboot
mode. As we only have one BootROM, we can improve usability by adding a
global flag that describes whether a restart handler is suitable for
use after a bootrom reboot mode write. Add a flag bit describing this
and allow populating it from the device tree as well as from drivers.
Existing i.MX/STM32 drivers will be moved onto this in follow-up
commits.
Signed-off-by: Ahmad Fatoum <a.fatoum@pengutronix.de>
---
Documentation/boards/imx.rst | 2 +-
.../devicetree/bindings/power/restart.rst | 5 +++++
Documentation/user/reboot-mode.rst | 7 ++++++-
commands/reset.c | 16 ++++++++++------
common/restart.c | 17 +++++++++++++----
include/restart.h | 5 ++++-
6 files changed, 39 insertions(+), 13 deletions(-)
diff --git a/Documentation/boards/imx.rst b/Documentation/boards/imx.rst
index 4ce9d9808cc1..6c16923340a8 100644
--- a/Documentation/boards/imx.rst
+++ b/Documentation/boards/imx.rst
@@ -105,7 +105,7 @@ that BootROM should select after a warm reset::
mode-serial = <0x10 0x40000000>;
};
- barebox@FSL i.MX8MM EVK board:/ gpr.reboot_mode.next=serial reset -r imxwd-warm
+ barebox@FSL i.MX8MM EVK board:/ gpr.reboot_mode.next=serial reset -w
This will cause barebox to fall into serial download mode on an i.MX8MM.
diff --git a/Documentation/devicetree/bindings/power/restart.rst b/Documentation/devicetree/bindings/power/restart.rst
index 8c866f6e0ded..42b87f7e9c65 100644
--- a/Documentation/devicetree/bindings/power/restart.rst
+++ b/Documentation/devicetree/bindings/power/restart.rst
@@ -8,3 +8,8 @@ Optional properties:
- ``restart-priority`` : Overrides the priority set by the driver. Normally,
the device with the biggest reach should reset the system.
See :ref:`_system_reset` for more information.
+
+- ``barebox,restart-warm-bootrom`` : Restart will not cause loss to non-volatile
+ registers sampled by the bootrom at startup. This is a necessary precondition
+ for working :ref:`reboot_mode` communication between barebox and the SoC's
+ BootROM.
diff --git a/Documentation/user/reboot-mode.rst b/Documentation/user/reboot-mode.rst
index 83d4136b8592..1929a67e0bc9 100644
--- a/Documentation/user/reboot-mode.rst
+++ b/Documentation/user/reboot-mode.rst
@@ -47,7 +47,9 @@ Reboot mode providers have priorities. The provider with the highest
priority has its parameters aliased as ``$global.system.reboot_mode.prev``
and ``$global.system.reboot_mode.next``. After executing the init scripts,
barebox startup will ``source /env/bmode/${global.system.reboot_mode.prev}``
-if available.
+if available. Example usage::
+
+ gpr.reboot_mode=serial reset -w
Reset
=====
@@ -60,6 +62,9 @@ If such reboot mode storage is used, users must take care to use the correct
reset provider. In barebox, multiple reset providers may co-exist. The
``reset`` command allows listing and choosing a specific reboot mode.
+For communication with the SoC's BootROM, a warm reset can be triggered
+with ``reset -w`` if a suitable reset handler has been registered.
+
Disambiguation
==============
diff --git a/commands/reset.c b/commands/reset.c
index fe54e2f9b472..88e677afab34 100644
--- a/commands/reset.c
+++ b/commands/reset.c
@@ -12,12 +12,12 @@
static int cmd_reset(int argc, char *argv[])
{
struct restart_handler *rst;
- int opt, shutdown_flag;
+ int opt, shutdown_flag, flags = 0;
const char *name = NULL;
shutdown_flag = 1;
- while ((opt = getopt(argc, argv, "flr:")) > 0) {
+ while ((opt = getopt(argc, argv, "flwr:")) > 0) {
switch (opt) {
case 'f':
shutdown_flag = 0;
@@ -25,6 +25,9 @@ static int cmd_reset(int argc, char *argv[])
case 'l':
restart_handlers_print();
return 0;
+ case 'w':
+ flags |= RESTART_FLAG_WARM_BOOTROM;
+ break;
case 'r':
name = optarg;
break;
@@ -33,9 +36,9 @@ static int cmd_reset(int argc, char *argv[])
}
}
- rst = restart_handler_get_by_name(name);
- if (!rst && name) {
- printf("reset '%s' does not exist\n", name);
+ rst = restart_handler_get_by_name(name, flags);
+ if (!rst && (name || flags)) {
+ printf("No matching restart handler found\n");
return COMMAND_ERROR;
}
@@ -57,13 +60,14 @@ BAREBOX_CMD_HELP_START(reset)
BAREBOX_CMD_HELP_TEXT("Options:")
BAREBOX_CMD_HELP_OPT("-f", "force RESET, don't call shutdown")
BAREBOX_CMD_HELP_OPT("-l", "list reset handlers")
+BAREBOX_CMD_HELP_OPT("-w", "only consider warm BootROM reboot-mode-preserving resets")
BAREBOX_CMD_HELP_OPT("-r RESET", "use reset handler named RESET")
BAREBOX_CMD_HELP_END
BAREBOX_CMD_START(reset)
.cmd = cmd_reset,
BAREBOX_CMD_DESC("perform RESET of the CPU")
- BAREBOX_CMD_OPTS("[-flr]")
+ BAREBOX_CMD_OPTS("[-flrw]")
BAREBOX_CMD_GROUP(CMD_GRP_BOOT)
BAREBOX_CMD_HELP(cmd_reset_help)
BAREBOX_CMD_COMPLETE(empty_complete)
diff --git a/common/restart.c b/common/restart.c
index 9e988838bc60..0294b36eccca 100644
--- a/common/restart.c
+++ b/common/restart.c
@@ -30,6 +30,9 @@ int restart_handler_register(struct restart_handler *rst)
if (rst->of_node) {
of_property_read_u32(rst->of_node, "restart-priority",
&rst->priority);
+ if (of_property_read_bool(rst->of_node,
+ "barebox,restart-warm-bootrom"))
+ rst->flags |= RESTART_FLAG_WARM_BOOTROM;
}
list_add_tail(&rst->list, &restart_handler_list);
@@ -73,7 +76,7 @@ int restart_handler_register_fn(const char *name,
/**
* restart_handler_get_by_name() - reset the whole system
*/
-struct restart_handler *restart_handler_get_by_name(const char *name)
+struct restart_handler *restart_handler_get_by_name(const char *name, int flags)
{
struct restart_handler *rst = NULL, *tmp;
unsigned int priority = 0;
@@ -81,6 +84,8 @@ struct restart_handler *restart_handler_get_by_name(const char *name)
list_for_each_entry(tmp, &restart_handler_list, list) {
if (name && tmp->name && strcmp(name, tmp->name))
continue;
+ if (flags && (tmp->flags & flags) != flags)
+ continue;
if (tmp->priority > priority) {
priority = tmp->priority;
rst = tmp;
@@ -97,7 +102,7 @@ void __noreturn restart_machine(void)
{
struct restart_handler *rst;
- rst = restart_handler_get_by_name(NULL);
+ rst = restart_handler_get_by_name(NULL, 0);
if (rst) {
pr_debug("%s: using restart handler %s\n", __func__, rst->name);
console_flush();
@@ -114,6 +119,10 @@ void restart_handlers_print(void)
{
struct restart_handler *tmp;
- list_for_each_entry(tmp, &restart_handler_list, list)
- printf("%-20s %6d\n", tmp->name, tmp->priority);
+ list_for_each_entry(tmp, &restart_handler_list, list) {
+ printf("%-20s %6d ", tmp->name, tmp->priority);
+ if (tmp->flags & RESTART_FLAG_WARM_BOOTROM)
+ putchar('W');
+ putchar('\n');
+ }
}
diff --git a/include/restart.h b/include/restart.h
index 330b50a53ab2..15f30bb7ad4d 100644
--- a/include/restart.h
+++ b/include/restart.h
@@ -4,18 +4,21 @@
#include <linux/compiler.h>
#include <linux/types.h>
+#include <linux/bitops.h>
struct device_node;
void restart_handlers_print(void);
void __noreturn restart_machine(void);
-struct restart_handler *restart_handler_get_by_name(const char *name);
+struct restart_handler *restart_handler_get_by_name(const char *name, int flags);
struct device_node;
struct restart_handler {
void (*restart)(struct restart_handler *);
int priority;
+#define RESTART_FLAG_WARM_BOOTROM BIT(0)
+ int flags;
struct device_node *of_node;
const char *name;
struct list_head list;
--
2.30.2
^ permalink raw reply [flat|nested] 10+ messages in thread
* [PATCH 4/8] watchdog: imxwd: don't register broken imxwd-warm for i.MX7
2022-10-17 7:09 [PATCH 0/8] ARM: i.MX7: add serial download reboot mode Ahmad Fatoum
` (2 preceding siblings ...)
2022-10-17 7:09 ` [PATCH 3/8] restart: add reset -w for warm bootrom reset Ahmad Fatoum
@ 2022-10-17 7:09 ` Ahmad Fatoum
2022-10-17 7:09 ` [PATCH 5/8] watchdog: imxwd: set imxwd-warm as reboot mode default handler Ahmad Fatoum
` (4 subsequent siblings)
8 siblings, 0 replies; 10+ messages in thread
From: Ahmad Fatoum @ 2022-10-17 7:09 UTC (permalink / raw)
To: barebox; +Cc: Ahmad Fatoum
Due to erratum e10574 "Watchdog: A watchdog timeout or software trigger
will not reset the SOC", any use of the watchdog reset must trigger an
external PMIC or reset circuit. Registering imxwd-warm thus serves no
purpose, so don't register it for i.MX7. We'll need an alternative for
reboot mode, which will follow in a later commit.
Signed-off-by: Ahmad Fatoum <a.fatoum@pengutronix.de>
---
drivers/watchdog/imxwd.c | 30 +++++++++++++++++++++++-------
1 file changed, 23 insertions(+), 7 deletions(-)
diff --git a/drivers/watchdog/imxwd.c b/drivers/watchdog/imxwd.c
index dba92cb46afb..b669f6702d62 100644
--- a/drivers/watchdog/imxwd.c
+++ b/drivers/watchdog/imxwd.c
@@ -213,7 +213,7 @@ static void imx_watchdog_detect_reset_source(struct imx_wd *priv)
/* else keep the default 'unknown' state */
}
-static int imx21_wd_init(struct imx_wd *priv)
+static int imx21_wd_init_no_warm_reset(struct imx_wd *priv)
{
imx_watchdog_detect_reset_source(priv);
@@ -225,6 +225,17 @@ static int imx21_wd_init(struct imx_wd *priv)
return 0;
}
+static int imx21_wd_init(struct imx_wd *priv)
+{
+ priv->restart_warm.name = "imxwd-warm";
+ priv->restart_warm.restart = imxwd_force_soc_reset_internal;
+ priv->restart_warm.priority = RESTART_DEFAULT_PRIORITY - 10;
+
+ restart_handler_register(&priv->restart_warm);
+
+ return imx21_wd_init_no_warm_reset(priv);
+}
+
static int imx_wd_probe(struct device_d *dev)
{
struct resource *iores;
@@ -294,12 +305,6 @@ static int imx_wd_probe(struct device_d *dev)
restart_handler_register(&priv->restart);
- priv->restart_warm.name = "imxwd-warm";
- priv->restart_warm.restart = imxwd_force_soc_reset_internal;
- priv->restart_warm.priority = RESTART_DEFAULT_PRIORITY - 10;
-
- restart_handler_register(&priv->restart_warm);
-
return 0;
error_unregister:
@@ -310,6 +315,14 @@ on_error:
return ret;
}
+static const struct imx_wd_ops imx7d_wd_ops = {
+ .set_timeout = imx21_watchdog_set_timeout,
+ .soc_reset = imx21_soc_reset,
+ .init = imx21_wd_init_no_warm_reset,
+ .is_running = imx21_watchdog_is_running,
+ .timeout_max = 128,
+};
+
static const struct imx_wd_ops imx21_wd_ops = {
.set_timeout = imx21_watchdog_set_timeout,
.soc_reset = imx21_soc_reset,
@@ -331,6 +344,9 @@ static __maybe_unused struct of_device_id imx_wdt_dt_ids[] = {
}, {
.compatible = "fsl,imx21-wdt",
.data = &imx21_wd_ops,
+ }, {
+ .compatible = "fsl,imx7d-wdt",
+ .data = &imx7d_wd_ops,
}, {
/* sentinel */
}
--
2.30.2
^ permalink raw reply [flat|nested] 10+ messages in thread
* [PATCH 5/8] watchdog: imxwd: set imxwd-warm as reboot mode default handler
2022-10-17 7:09 [PATCH 0/8] ARM: i.MX7: add serial download reboot mode Ahmad Fatoum
` (3 preceding siblings ...)
2022-10-17 7:09 ` [PATCH 4/8] watchdog: imxwd: don't register broken imxwd-warm for i.MX7 Ahmad Fatoum
@ 2022-10-17 7:09 ` Ahmad Fatoum
2022-10-17 7:09 ` [PATCH 6/8] Documentations: devicetree: bindings: document watchdog-priority Ahmad Fatoum
` (3 subsequent siblings)
8 siblings, 0 replies; 10+ messages in thread
From: Ahmad Fatoum @ 2022-10-17 7:09 UTC (permalink / raw)
To: barebox; +Cc: Ahmad Fatoum
Set RESTART_FLAG_WARM_BOOTROM for imxwd-warm, so reset -w directly
selects this handler. i.MX6QDL/8MM Users now can just do
gpr.reboot_mode.next=serial reset -w
and it should behave as expected.
Signed-off-by: Ahmad Fatoum <a.fatoum@pengutronix.de>
---
drivers/watchdog/imxwd.c | 1 +
1 file changed, 1 insertion(+)
diff --git a/drivers/watchdog/imxwd.c b/drivers/watchdog/imxwd.c
index b669f6702d62..5e9962866f54 100644
--- a/drivers/watchdog/imxwd.c
+++ b/drivers/watchdog/imxwd.c
@@ -230,6 +230,7 @@ static int imx21_wd_init(struct imx_wd *priv)
priv->restart_warm.name = "imxwd-warm";
priv->restart_warm.restart = imxwd_force_soc_reset_internal;
priv->restart_warm.priority = RESTART_DEFAULT_PRIORITY - 10;
+ priv->restart_warm.flags = RESTART_FLAG_WARM_BOOTROM;
restart_handler_register(&priv->restart_warm);
--
2.30.2
^ permalink raw reply [flat|nested] 10+ messages in thread
* [PATCH 6/8] Documentations: devicetree: bindings: document watchdog-priority
2022-10-17 7:09 [PATCH 0/8] ARM: i.MX7: add serial download reboot mode Ahmad Fatoum
` (4 preceding siblings ...)
2022-10-17 7:09 ` [PATCH 5/8] watchdog: imxwd: set imxwd-warm as reboot mode default handler Ahmad Fatoum
@ 2022-10-17 7:09 ` Ahmad Fatoum
2022-10-17 7:09 ` [PATCH 7/8] ARM: i.MX7: describe USB serial download boot mode Ahmad Fatoum
` (2 subsequent siblings)
8 siblings, 0 replies; 10+ messages in thread
From: Ahmad Fatoum @ 2022-10-17 7:09 UTC (permalink / raw)
To: barebox; +Cc: Ahmad Fatoum
We parse watchdog-priority for every OF-enabled watchdog device, but
failed to document it. Remedy this.
Signed-off-by: Ahmad Fatoum <a.fatoum@pengutronix.de>
---
.../devicetree/bindings/watchdog/watchdog.rst | 10 ++++++++++
1 file changed, 10 insertions(+)
create mode 100644 Documentation/devicetree/bindings/watchdog/watchdog.rst
diff --git a/Documentation/devicetree/bindings/watchdog/watchdog.rst b/Documentation/devicetree/bindings/watchdog/watchdog.rst
new file mode 100644
index 000000000000..415a4520f45e
--- /dev/null
+++ b/Documentation/devicetree/bindings/watchdog/watchdog.rst
@@ -0,0 +1,10 @@
+Watchdogs
+=========
+
+In addition to the upstream bindings, following properties are understood:
+
+Optional properties:
+
+- ``watchdog-priority`` : Overrides the priority set by the driver. Normally,
+ the watchdog device with the biggest reach should reset the system.
+ See :ref:`_system_reset` for more information.
--
2.30.2
^ permalink raw reply [flat|nested] 10+ messages in thread
* [PATCH 7/8] ARM: i.MX7: describe USB serial download boot mode
2022-10-17 7:09 [PATCH 0/8] ARM: i.MX7: add serial download reboot mode Ahmad Fatoum
` (5 preceding siblings ...)
2022-10-17 7:09 ` [PATCH 6/8] Documentations: devicetree: bindings: document watchdog-priority Ahmad Fatoum
@ 2022-10-17 7:09 ` Ahmad Fatoum
2022-10-17 7:10 ` [PATCH 8/8] ARM: stm32mp: mark iwdg2 with barebox,restart-warm-bootrom Ahmad Fatoum
2022-10-18 9:13 ` [PATCH 0/8] ARM: i.MX7: add serial download reboot mode Sascha Hauer
8 siblings, 0 replies; 10+ messages in thread
From: Ahmad Fatoum @ 2022-10-17 7:09 UTC (permalink / raw)
To: barebox; +Cc: Ahmad Fatoum
Due to i.MX7 erratum e10574: "Watchdog: A watchdog timeout or software
trigger will not reset the SOC", we can't do warm reset via imxwd-warm
for BootROM reboot mode as we do on other i.MX SoCs.
What we can do instead though, is use the SoC's reset controller to
toggle the Cortex-A7's reset. This will have us reenter BootROM with
GPR registers intact. Forcing serial download on the i.MX7 now possible
with:
gpr.reboot_mode.next=serial reset -w
Note that the new restart handler is not fit for general purpose.
Depending on boot medium, it may hang, because the BootROM may not
reinitialize the peripheral properly.
Signed-off-by: Ahmad Fatoum <a.fatoum@pengutronix.de>
---
arch/arm/configs/imx_v7_defconfig | 2 ++
arch/arm/dts/imx7.dtsi | 37 +++++++++++++++++++++++++++++
drivers/power/reset/syscon-reboot.c | 1 +
3 files changed, 40 insertions(+)
create mode 100644 arch/arm/dts/imx7.dtsi
diff --git a/arch/arm/configs/imx_v7_defconfig b/arch/arm/configs/imx_v7_defconfig
index d07abe28aeac..3cbec267fc87 100644
--- a/arch/arm/configs/imx_v7_defconfig
+++ b/arch/arm/configs/imx_v7_defconfig
@@ -208,6 +208,8 @@ CONFIG_REGULATOR=y
CONFIG_REGULATOR_FIXED=y
CONFIG_GENERIC_PHY=y
CONFIG_USB_NOP_XCEIV=y
+CONFIG_SYSCON_REBOOT_MODE=y
+CONFIG_POWER_RESET_SYSCON=y
CONFIG_FS_EXT4=y
CONFIG_FS_TFTP=y
CONFIG_FS_TFTP_MAX_WINDOW_SIZE=8
diff --git a/arch/arm/dts/imx7.dtsi b/arch/arm/dts/imx7.dtsi
new file mode 100644
index 000000000000..1c67bdc54620
--- /dev/null
+++ b/arch/arm/dts/imx7.dtsi
@@ -0,0 +1,37 @@
+/* SPDX-License-Identifier: GPL-2.0-only OR MIT */
+
+#include "imx7d-ddrc.dtsi"
+
+/ {
+ aliases {
+ gpr.reboot_mode = &reboot_mode_gpr;
+ };
+};
+
+&src {
+ compatible = "fsl,imx7d-src", "syscon", "simple-mfd";
+
+ reboot_mode_gpr: reboot-mode {
+ compatible = "barebox,syscon-reboot-mode";
+ offset = <0x94>, <0x98>; /* SRC_GPR{9,10} */
+ mask = <0xffffffff>, <0x40000000>;
+ mode-normal = <0>, <0>;
+ mode-serial = <0x00000010>, <0x40000000>;
+ };
+
+ ca7_reset: cortex-a7-reboot {
+ compatible = "syscon-reboot";
+ regmap = <&src>;
+ offset = <0x4>;
+ mask = <1>;
+ value = <1>;
+ /* This is not fit for use as general purpose reset */
+ restart-priority = <5>;
+ /*
+ * Can't use imxwd-warm due to errata e10574:
+ * Watchdog: A watchdog timeout or software trigger will
+ * not reset the SOC
+ */
+ barebox,restart-warm-bootrom;
+ };
+};
diff --git a/drivers/power/reset/syscon-reboot.c b/drivers/power/reset/syscon-reboot.c
index 2dbb6c1ddcb8..b6b8db75caba 100644
--- a/drivers/power/reset/syscon-reboot.c
+++ b/drivers/power/reset/syscon-reboot.c
@@ -71,6 +71,7 @@ static int syscon_reboot_probe(struct device_d *dev)
ctx->restart_handler.name = "syscon-reboot";
ctx->restart_handler.restart = syscon_restart_handle;
ctx->restart_handler.priority = 192;
+ ctx->restart_handler.of_node = dev->device_node;
err = restart_handler_register(&ctx->restart_handler);
if (err)
--
2.30.2
^ permalink raw reply [flat|nested] 10+ messages in thread
* [PATCH 8/8] ARM: stm32mp: mark iwdg2 with barebox,restart-warm-bootrom
2022-10-17 7:09 [PATCH 0/8] ARM: i.MX7: add serial download reboot mode Ahmad Fatoum
` (6 preceding siblings ...)
2022-10-17 7:09 ` [PATCH 7/8] ARM: i.MX7: describe USB serial download boot mode Ahmad Fatoum
@ 2022-10-17 7:10 ` Ahmad Fatoum
2022-10-18 9:13 ` [PATCH 0/8] ARM: i.MX7: add serial download reboot mode Sascha Hauer
8 siblings, 0 replies; 10+ messages in thread
From: Ahmad Fatoum @ 2022-10-17 7:10 UTC (permalink / raw)
To: barebox; +Cc: Ahmad Fatoum
All STM32MP1 DTs already include their respective barebox SoC header, so
set barebox,restart-warm-bootrom there, so users can portably run:
tamp.reboot_mode.next=serial reset -w
To get into DFU mode.
Signed-off-by: Ahmad Fatoum <a.fatoum@pengutronix.de>
---
Documentation/boards/stm32mp.rst | 6 +++++-
arch/arm/dts/stm32mp131.dtsi | 4 ++++
arch/arm/dts/stm32mp151.dtsi | 4 ++++
drivers/clk/clk-stm32mp1.c | 2 +-
drivers/power/reset/stm32-reboot.c | 6 ++++--
include/soc/stm32/reboot.h | 6 ++++--
6 files changed, 22 insertions(+), 6 deletions(-)
diff --git a/Documentation/boards/stm32mp.rst b/Documentation/boards/stm32mp.rst
index 4cdd281a9e14..813117a04f22 100644
--- a/Documentation/boards/stm32mp.rst
+++ b/Documentation/boards/stm32mp.rst
@@ -164,9 +164,13 @@ normal barebox functionality like creating a DFU-gadget in barebox,
Fastboot/USB mass storage ... etc.
The FIP image containing barebox can be generated as described in
-137::ref:`stm32mp_fip`. Upstream TF-A doesn't support DFU for
+:ref:`stm32mp_fip`. Upstream TF-A doesn't support DFU for
SSBLs using the legacy stm32image format.
+DFU mode can be forced via :ref:`reboot_mode` from a booted system with::
+
+ tamp.reboot_mode.next=serial reset -w
+
Boot source selection
---------------------
diff --git a/arch/arm/dts/stm32mp131.dtsi b/arch/arm/dts/stm32mp131.dtsi
index 2ecad85f086e..89a7ffcb814f 100644
--- a/arch/arm/dts/stm32mp131.dtsi
+++ b/arch/arm/dts/stm32mp131.dtsi
@@ -12,3 +12,7 @@
reg = <0x5a003000 0x1000>;
};
};
+
+&iwdg2 {
+ barebox,restart-warm-bootrom;
+};
diff --git a/arch/arm/dts/stm32mp151.dtsi b/arch/arm/dts/stm32mp151.dtsi
index ac6536a556a9..d3e924dc0072 100644
--- a/arch/arm/dts/stm32mp151.dtsi
+++ b/arch/arm/dts/stm32mp151.dtsi
@@ -37,6 +37,10 @@
barebox,provide-mac-address = <ðernet0 0x39>;
};
+&iwdg2 {
+ barebox,restart-warm-bootrom;
+};
+
&tamp {
reboot_mode_tamp: reboot-mode {
compatible = "syscon-reboot-mode";
diff --git a/drivers/clk/clk-stm32mp1.c b/drivers/clk/clk-stm32mp1.c
index c4b03e9f6d74..6753a3689085 100644
--- a/drivers/clk/clk-stm32mp1.c
+++ b/drivers/clk/clk-stm32mp1.c
@@ -2280,7 +2280,7 @@ static int stm32mp1_rcc_init(struct device_d *dev)
if (ret)
return ret;
- stm32mp_system_restart_init(base);
+ stm32mp_system_restart_init(dev);
return 0;
}
diff --git a/drivers/power/reset/stm32-reboot.c b/drivers/power/reset/stm32-reboot.c
index 809531e71396..147b4d9d8164 100644
--- a/drivers/power/reset/stm32-reboot.c
+++ b/drivers/power/reset/stm32-reboot.c
@@ -108,17 +108,19 @@ static void stm32_set_reset_reason(struct stm32_reset *priv,
reset_source_to_string(type), reg);
}
-void stm32mp_system_restart_init(void __iomem *base)
+void stm32mp_system_restart_init(struct device_d *dev)
{
struct stm32_reset *priv;
+ struct device_node *np = dev_of_node(dev);
priv = xzalloc(sizeof(*priv));
- priv->base = base;
+ priv->base = of_iomap(np, 0);
priv->restart.name = "stm32-rcc";
priv->restart.restart = stm32mp_rcc_restart_handler;
priv->restart.priority = 200;
+ priv->restart.of_node = np;
restart_handler_register(&priv->restart);
diff --git a/include/soc/stm32/reboot.h b/include/soc/stm32/reboot.h
index d6c731f59f74..cf0d0286e753 100644
--- a/include/soc/stm32/reboot.h
+++ b/include/soc/stm32/reboot.h
@@ -5,10 +5,12 @@
#include <linux/compiler.h>
+struct device_d;
+
#ifdef CONFIG_RESET_STM32
-void stm32mp_system_restart_init(void __iomem *rcc);
+void stm32mp_system_restart_init(struct device_d *rcc);
#else
-static inline void stm32mp_system_restart_init(void __iomem *rcc)
+static inline void stm32mp_system_restart_init(struct device_d *rcc)
{
}
#endif
--
2.30.2
^ permalink raw reply [flat|nested] 10+ messages in thread
* Re: [PATCH 0/8] ARM: i.MX7: add serial download reboot mode
2022-10-17 7:09 [PATCH 0/8] ARM: i.MX7: add serial download reboot mode Ahmad Fatoum
` (7 preceding siblings ...)
2022-10-17 7:10 ` [PATCH 8/8] ARM: stm32mp: mark iwdg2 with barebox,restart-warm-bootrom Ahmad Fatoum
@ 2022-10-18 9:13 ` Sascha Hauer
8 siblings, 0 replies; 10+ messages in thread
From: Sascha Hauer @ 2022-10-18 9:13 UTC (permalink / raw)
To: Ahmad Fatoum; +Cc: barebox
On Mon, Oct 17, 2022 at 09:09:52AM +0200, Ahmad Fatoum wrote:
> BootROM can be forced into USB recovery on i.MX7 just like on the
> i.MX8M, with the difference that reset is a bit more involved,
> because warm resets via watchdogs are broken on this SoC.
>
> We do a bit of cleanup and then tackle that via a syscon-reboot
> device describing the Cortex-A7 CPU0 reset.
>
> Ahmad Fatoum (8):
> restart: make restart.h header self-contained
> restart: do restart-priority OF parsing in restart_handler_register
> restart: add reset -w for warm bootrom reset
> watchdog: imxwd: don't register broken imxwd-warm for i.MX7
> watchdog: imxwd: set imxwd-warm as reboot mode default handler
> Documentations: devicetree: bindings: document watchdog-priority
> ARM: i.MX7: describe USB serial download boot mode
> ARM: stm32mp: mark iwdg2 with barebox,restart-warm-bootrom
Applied, thanks
Sascha
>
> Documentation/boards/imx.rst | 2 +-
> Documentation/boards/stm32mp.rst | 6 ++-
> .../devicetree/bindings/power/restart.rst | 15 ++++++++
> .../devicetree/bindings/watchdog/watchdog.rst | 10 +++++
> Documentation/user/reboot-mode.rst | 7 +++-
> arch/arm/configs/imx_v7_defconfig | 2 +
> arch/arm/dts/imx7.dtsi | 37 +++++++++++++++++++
> arch/arm/dts/stm32mp131.dtsi | 4 ++
> arch/arm/dts/stm32mp151.dtsi | 4 ++
> commands/reset.c | 16 +++++---
> common/restart.c | 37 +++++++++----------
> drivers/clk/clk-stm32mp1.c | 2 +-
> drivers/mfd/da9053.c | 2 +-
> drivers/mfd/da9063.c | 2 +-
> drivers/mfd/rn5t568.c | 2 +-
> drivers/power/reset/stm32-reboot.c | 6 ++-
> drivers/power/reset/syscon-reboot.c | 1 +
> drivers/watchdog/imxwd.c | 31 ++++++++++++----
> include/restart.h | 15 ++++++--
> include/soc/stm32/reboot.h | 6 ++-
> 20 files changed, 161 insertions(+), 46 deletions(-)
> create mode 100644 Documentation/devicetree/bindings/power/restart.rst
> create mode 100644 Documentation/devicetree/bindings/watchdog/watchdog.rst
> create mode 100644 arch/arm/dts/imx7.dtsi
>
> --
> 2.30.2
>
>
>
--
Pengutronix e.K. | |
Steuerwalder Str. 21 | http://www.pengutronix.de/ |
31137 Hildesheim, Germany | Phone: +49-5121-206917-0 |
Amtsgericht Hildesheim, HRA 2686 | Fax: +49-5121-206917-5555 |
^ permalink raw reply [flat|nested] 10+ messages in thread
end of thread, other threads:[~2022-10-18 9:15 UTC | newest]
Thread overview: 10+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2022-10-17 7:09 [PATCH 0/8] ARM: i.MX7: add serial download reboot mode Ahmad Fatoum
2022-10-17 7:09 ` [PATCH 1/8] restart: make restart.h header self-contained Ahmad Fatoum
2022-10-17 7:09 ` [PATCH 2/8] restart: do restart-priority OF parsing in restart_handler_register Ahmad Fatoum
2022-10-17 7:09 ` [PATCH 3/8] restart: add reset -w for warm bootrom reset Ahmad Fatoum
2022-10-17 7:09 ` [PATCH 4/8] watchdog: imxwd: don't register broken imxwd-warm for i.MX7 Ahmad Fatoum
2022-10-17 7:09 ` [PATCH 5/8] watchdog: imxwd: set imxwd-warm as reboot mode default handler Ahmad Fatoum
2022-10-17 7:09 ` [PATCH 6/8] Documentations: devicetree: bindings: document watchdog-priority Ahmad Fatoum
2022-10-17 7:09 ` [PATCH 7/8] ARM: i.MX7: describe USB serial download boot mode Ahmad Fatoum
2022-10-17 7:10 ` [PATCH 8/8] ARM: stm32mp: mark iwdg2 with barebox,restart-warm-bootrom Ahmad Fatoum
2022-10-18 9:13 ` [PATCH 0/8] ARM: i.MX7: add serial download reboot mode Sascha Hauer
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox