@@ -91,6 +91,7 @@ extern enum es_result sev_es_ghcb_hv_call(struct ghcb *ghcb,
u64 exit_code, u64 exit_info_1,
u64 exit_info_2);
void sev_es_stop_this_cpu(void);
+bool sev_kexec_supported(void);
#else
static inline void sev_es_ist_enter(struct pt_regs *regs) { }
static inline void sev_es_ist_exit(void) { }
@@ -98,6 +99,7 @@ static inline int sev_es_setup_ap_jump_table(struct real_mode_header *rmh) { ret
static inline void sev_es_nmi_complete(void) { }
static inline int sev_es_efi_map_ghcbs(pgd_t *pgd) { return 0; }
static inline void sev_es_stop_this_cpu(void) { }
+static inline bool sev_kexec_supported(void) { return true; }
#endif
#endif
@@ -27,6 +27,7 @@
#include <asm/kexec-bzimage64.h>
#include <asm/setup.h>
#include <asm/set_memory.h>
+#include <asm/sev.h>
#ifdef CONFIG_ACPI
/*
@@ -271,7 +272,7 @@ static void load_segments(void)
static bool machine_kexec_supported(void)
{
- if (cc_platform_has(CC_ATTR_GUEST_STATE_ENCRYPT))
+ if (!sev_kexec_supported())
return false;
return true;
@@ -884,6 +884,21 @@ static int __init sev_setup_ap_jump_table(void)
}
core_initcall(sev_setup_ap_jump_table);
+bool sev_kexec_supported(void)
+{
+ if (!cc_platform_has(CC_ATTR_GUEST_STATE_ENCRYPT))
+ return true;
+
+ /*
+ * KEXEC with SEV-ES and more than one CPU is only supported
+ * when the AP jump table is installed.
+ */
+ if (num_possible_cpus() > 1)
+ return sev_ap_jumptable_blob_installed;
+ else
+ return true;
+}
+
static void __init alloc_runtime_data(int cpu)
{
struct sev_es_runtime_data *data;