diff options
author | Jack Rosenthal <jrosenth@chromium.org> | 2019-04-22 10:56:10 -0600 |
---|---|---|
committer | chrome-bot <chrome-bot@chromium.org> | 2019-04-24 15:52:07 -0700 |
commit | 2ece52589486990cca666dc3ebc4164d5f2c0aed (patch) | |
tree | 0278f08782a2cf34827568065773e6eec7f6b4ac /core | |
parent | 3fc3edd0d8f4a445965c4a936db02b03d37bc215 (diff) | |
download | chrome-ec-2ece52589486990cca666dc3ebc4164d5f2c0aed.tar.gz |
minute-ia: hard reset if we panic while handling a panic
ish_pm_reset is a rather complex procedure, and encountering a panic
while it is happening could lead to an infinte loop of handling
panics. This will preform a reset of the Minute-IA core if a panic
occurs and the system is already resetting from panic.
BUG=b:130752748,b:130587334
BRANCH=none
TEST=copied some invalid opcodes into switch_to_aontask procedure,
observed the hard reset after forcing a panic
Change-Id: I43459d78da9b67297f84e3a736d3f92da42a814c
Signed-off-by: Jack Rosenthal <jrosenth@chromium.org>
Reviewed-on: https://chromium-review.googlesource.com/1576835
Reviewed-by: Jett Rink <jettrink@chromium.org>
Diffstat (limited to 'core')
-rw-r--r-- | core/minute-ia/panic.c | 22 |
1 files changed, 19 insertions, 3 deletions
diff --git a/core/minute-ia/panic.c b/core/minute-ia/panic.c index eda38abc7f..06c903be0c 100644 --- a/core/minute-ia/panic.c +++ b/core/minute-ia/panic.c @@ -93,6 +93,14 @@ __attribute__ ((noreturn)) void __keep exception_panic( uint32_t cs, uint32_t eflags) { + /* + * If a panic were to occur during the reset procedure, we want + * to make sure that this panic will certainly cause a hard + * reset, rather than aontaskfw reset. Track if paniced once + * already. + */ + static int panic_once; + register uint32_t eax asm("eax"); register uint32_t ebx asm("ebx"); register uint32_t ecx asm("ecx"); @@ -121,10 +129,18 @@ __attribute__ ((noreturn)) void __keep exception_panic( PANIC_DATA_PTR->magic = PANIC_DATA_MAGIC; /* Display the panic and reset */ + if (panic_once) + panic_printf("\nWhile resetting from a panic, another panic" + " occurred!"); panic_data_print(PANIC_DATA_PTR); - system_reset(SYSTEM_RESET_HARD); - while (1) - continue; + if (panic_once) { + system_reset(SYSTEM_RESET_HARD); + } else { + panic_once = 1; + system_reset(0); + } + + __builtin_unreachable(); } #ifdef CONFIG_SOFTWARE_PANIC |