diff options
author | Nicholas Piggin <npiggin@gmail.com> | 2017-02-08 18:34:16 +1000 |
---|---|---|
committer | Stewart Smith <stewart@linux.vnet.ibm.com> | 2017-03-07 15:40:20 +1100 |
commit | 139e32d139103fc7fcb2121146c89edb9f40c55f (patch) | |
tree | 81488319384125d77350c3eb4c2237132977e0ab | |
parent | 28e96ffaba8b659f48312bdcea35a1403310fba3 (diff) | |
download | skiboot-139e32d139103fc7fcb2121146c89edb9f40c55f.zip skiboot-139e32d139103fc7fcb2121146c89edb9f40c55f.tar.gz skiboot-139e32d139103fc7fcb2121146c89edb9f40c55f.tar.bz2 |
System reset IPI facility and Mambo implementation
Add an opal call OPAL_SIGNAL_SYSTEM_RESET which allows system reset
exceptions to be raised on other CPUs and act as an NMI IPI. There
is an initial simple Mambo implementation, but allowances are made
for a more complex hardware implementation.
This API is based on the POWER8 implementation from Alistair Popple.
Signed-off-by: Nicholas Piggin <npiggin@gmail.com>
[stewart@linux.vnet.ibm.com: minor RST fix]
Signed-off-by: Stewart Smith <stewart@linux.vnet.ibm.com>
-rw-r--r-- | doc/opal-api/opal-signal-system-reset-145.rst | 44 | ||||
-rw-r--r-- | include/opal-api.h | 3 | ||||
-rw-r--r-- | platforms/mambo/mambo.c | 52 |
3 files changed, 98 insertions, 1 deletions
diff --git a/doc/opal-api/opal-signal-system-reset-145.rst b/doc/opal-api/opal-signal-system-reset-145.rst new file mode 100644 index 0000000..4c1ee93 --- /dev/null +++ b/doc/opal-api/opal-signal-system-reset-145.rst @@ -0,0 +1,44 @@ +OPAL_SIGNAL_SYSTEM_RESET +======================== +:: + + int64_t signal_system_reset(int32_t cpu_nr); + +This OPAL call causes the specified cpu(s) to be reset to the system +reset exception handler (0x100). + +The exact contents of system registers (e.g., SRR1 wakeup causes) may +vary depending on implementation and should not be relied upon. + +Resetting active threads on the same core as this call is run may +not be supported by some platforms. In that case, OPAL_PARTIAL will be +returned and NONE of the interrupts will be delivered. + +Arguments +--------- +:: + + int32_t cpu_nr + cpu_nr >= 0 The cpu server number of the target cpu to reset. + SYS_RESET_ALL (-1) All cpus should be reset. + SYS_RESET_ALL_OTHERS (-2) All but the current cpu should be reset. + +Returns +------- +OPAL_SUCCESS + The power down was updated successful. + +OPAL_PARAMETER + A parameter was incorrect. + +OPAL_HARDWARE + Hardware indicated failure during reset. + +OPAL_PARTIAL + Platform can not reset all requested CPUs at this time. This requires + platform-specific code to work around, otherwise to be treated as + failure. No CPUs are reset. + +OPAL_UNSUPPORTED + This processor/platform is not supported. + diff --git a/include/opal-api.h b/include/opal-api.h index 96e86e2..b814060 100644 --- a/include/opal-api.h +++ b/include/opal-api.h @@ -200,7 +200,8 @@ #define OPAL_XIVE_DUMP 142 #define OPAL_XIVE_RESERVED3 143 #define OPAL_XIVE_RESERVED4 144 -#define OPAL_LAST 144 +#define OPAL_SIGNAL_SYSTEM_RESET 145 +#define OPAL_LAST 145 /* Device tree flags */ diff --git a/platforms/mambo/mambo.c b/platforms/mambo/mambo.c index 976efea..cb6e103 100644 --- a/platforms/mambo/mambo.c +++ b/platforms/mambo/mambo.c @@ -19,6 +19,7 @@ #include <device.h> #include <console.h> #include <chip.h> +#include <cpu.h> #include <opal-api.h> #include <opal-internal.h> #include <time-utils.h> @@ -211,8 +212,59 @@ static void mambo_rtc_init(void) opal_register(OPAL_RTC_READ, mambo_rtc_read, 2); } +static void mambo_system_reset_cpu(struct cpu_thread *cpu) +{ + uint32_t core_id; + uint32_t thread_id; + char tcl_cmd[50]; + + core_id = pir_to_core_id(cpu->pir); + thread_id = pir_to_thread_id(cpu->pir); + + snprintf(tcl_cmd, sizeof(tcl_cmd), "mysim cpu %i:%i interrupt SystemReset", core_id, thread_id); + callthru_tcl(tcl_cmd, strlen(tcl_cmd)); +} + +#define SYS_RESET_ALL -1 +#define SYS_RESET_ALL_OTHERS -2 + +static int64_t mambo_signal_system_reset(int32_t cpu_nr) +{ + struct cpu_thread *cpu; + + if (cpu_nr < 0) { + if (cpu_nr < SYS_RESET_ALL_OTHERS) + return OPAL_PARAMETER; + + for_each_cpu(cpu) { + if (cpu == this_cpu()) + continue; + mambo_system_reset_cpu(cpu); + + } + if (cpu_nr == SYS_RESET_ALL) + mambo_system_reset_cpu(this_cpu()); + + return OPAL_SUCCESS; + + } else { + cpu = find_cpu_by_server(cpu_nr); + if (!cpu) + return OPAL_PARAMETER; + + mambo_system_reset_cpu(cpu); + return OPAL_SUCCESS; + } +} + +static void mambo_sreset_init(void) +{ + opal_register(OPAL_SIGNAL_SYSTEM_RESET, mambo_signal_system_reset, 1); +} + static void mambo_platform_init(void) { + mambo_sreset_init(); mambo_rtc_init(); bogus_disk_flash_init(); } |