mirror of
https://github.com/torvalds/linux.git
synced 2026-05-27 00:22:00 +02:00
- Largely cleanups along with a change to save XSS to the GHCB (Guest-Host
Communication Block) in SEV-ES guests so that the hypervisor can determine
the guest's XSAVES buffer size properly and thus support shadow stacks in
AMD confidential guests
-----BEGIN PGP SIGNATURE-----
iQIzBAABCgAdFiEEzv7L6UO9uDPlPSfHEsHwGGHeVUoFAmkttt0ACgkQEsHwGGHe
VUoaFg/8CY+UAE1VtnaWhG7hpxCqBLlVtyt3gVhIn6ZCZ5mxtFoEcZI8BnxnFbbM
Rpd+5LsMbu4GWfq/AEx/a+IT3rKZIT1RjRrd73JZZYRNpv6/Vnmv/7OizjDbBqhU
n3Q1rHJCaVk90oP2sbB4dr9qsYHOx624jz0CrBxUM7GnaCQwtofqa6hK6HMJDu3g
OLjJCoaHY0ry779QUjCmMJ1BbOLsy1fGsmuQO8LcE6xWRJv5ueJPcZbH0I0g5UIF
NExe03uxaSvrM0ZYdjHpQU590kyPwjzo0Jx8IANQDb0dyY4mIFPdnZwbRBr/OPnZ
205c0EllHZvDZ4nKTYfeJYjXnPWmovHXJATr/BuqW+0GQZYmTbDq2IgvbbnE9gs1
67Sy94ISuxs683hNb9U2cLI7OFHcVDGfESuHhmeJTQsVY+VazL00p6azFP1ONpsn
N93GYK+ZFvOeFFssO/gm97jbkKyUH9PS2+TEbhijeQkZ/PYKVbObM89LDLSRrKC7
5mEFCZIKIehKLdSoAc8yTzKRE0piyK/PR6ykzP9A2rEjrSN2HDqvsR+nDr0hQ1/V
Uye4a8V0XiHyZsvD+AIYJnARGYdcnUCiezep81WaC55hn0sdqrhlqnycnkd+7fDE
MZF9epXCnIAA8IF7I5jCLfwTa1b6ouMhBxpwiMpaL9DGmQghWcM=
=GCGn
-----END PGP SIGNATURE-----
Merge tag 'x86_sev_for_v6.19_rc1' of git://git.kernel.org/pub/scm/linux/kernel/git/tip/tip
Pull x86 SEV updates from Borislav Petkov:
- Largely cleanups along with a change to save XSS to the GHCB
(Guest-Host Communication Block) in SEV-ES guests so that the
hypervisor can determine the guest's XSAVES buffer size properly
and thus support shadow stacks in AMD confidential guests
* tag 'x86_sev_for_v6.19_rc1' of git://git.kernel.org/pub/scm/linux/kernel/git/tip/tip:
x86/cc: Fix enum spelling to fix kernel-doc warnings
x86/boot: Drop unused sev_enable() fallback
x86/coco/sev: Convert has_cpuflag() to use cpu_feature_enabled()
x86/sev: Include XSS value in GHCB CPUID request
x86/boot: Move boot_*msr helpers to asm/shared/msr.h
This commit is contained in:
commit
cb502f0e5e
|
|
@ -152,17 +152,6 @@ bool insn_has_rep_prefix(struct insn *insn);
|
|||
void sev_insn_decode_init(void);
|
||||
bool early_setup_ghcb(void);
|
||||
#else
|
||||
static inline void sev_enable(struct boot_params *bp)
|
||||
{
|
||||
/*
|
||||
* bp->cc_blob_address should only be set by boot/compressed kernel.
|
||||
* Initialize it to 0 unconditionally (thus here in this stub too) to
|
||||
* ensure that uninitialized values from buggy bootloaders aren't
|
||||
* propagated.
|
||||
*/
|
||||
if (bp)
|
||||
bp->cc_blob_address = 0;
|
||||
}
|
||||
static inline void snp_check_features(void) { }
|
||||
static inline void sev_es_shutdown_ghcb(void) { }
|
||||
static inline bool sev_es_check_ghcb_fault(unsigned long address)
|
||||
|
|
|
|||
|
|
@ -14,6 +14,7 @@
|
|||
|
||||
#include <asm/bootparam.h>
|
||||
#include <asm/pgtable_types.h>
|
||||
#include <asm/shared/msr.h>
|
||||
#include <asm/sev.h>
|
||||
#include <asm/trapnr.h>
|
||||
#include <asm/trap_pf.h>
|
||||
|
|
@ -397,7 +398,7 @@ void sev_enable(struct boot_params *bp)
|
|||
}
|
||||
|
||||
/* Set the SME mask if this is an SEV guest. */
|
||||
boot_rdmsr(MSR_AMD64_SEV, &m);
|
||||
raw_rdmsr(MSR_AMD64_SEV, &m);
|
||||
sev_status = m.q;
|
||||
if (!(sev_status & MSR_AMD64_SEV_ENABLED))
|
||||
return;
|
||||
|
|
@ -446,7 +447,7 @@ u64 sev_get_status(void)
|
|||
if (sev_check_cpu_support() < 0)
|
||||
return 0;
|
||||
|
||||
boot_rdmsr(MSR_AMD64_SEV, &m);
|
||||
raw_rdmsr(MSR_AMD64_SEV, &m);
|
||||
return m.q;
|
||||
}
|
||||
|
||||
|
|
@ -496,7 +497,7 @@ bool early_is_sevsnp_guest(void)
|
|||
struct msr m;
|
||||
|
||||
/* Obtain the address of the calling area to use */
|
||||
boot_rdmsr(MSR_SVSM_CAA, &m);
|
||||
raw_rdmsr(MSR_SVSM_CAA, &m);
|
||||
boot_svsm_caa_pa = m.q;
|
||||
|
||||
/*
|
||||
|
|
|
|||
|
|
@ -10,7 +10,7 @@
|
|||
|
||||
#ifdef CONFIG_AMD_MEM_ENCRYPT
|
||||
|
||||
#include "../msr.h"
|
||||
#include <asm/shared/msr.h>
|
||||
|
||||
void snp_accept_memory(phys_addr_t start, phys_addr_t end);
|
||||
u64 sev_get_status(void);
|
||||
|
|
@ -20,7 +20,7 @@ static inline u64 sev_es_rd_ghcb_msr(void)
|
|||
{
|
||||
struct msr m;
|
||||
|
||||
boot_rdmsr(MSR_AMD64_SEV_ES_GHCB, &m);
|
||||
raw_rdmsr(MSR_AMD64_SEV_ES_GHCB, &m);
|
||||
|
||||
return m.q;
|
||||
}
|
||||
|
|
@ -30,7 +30,7 @@ static inline void sev_es_wr_ghcb_msr(u64 val)
|
|||
struct msr m;
|
||||
|
||||
m.q = val;
|
||||
boot_wrmsr(MSR_AMD64_SEV_ES_GHCB, &m);
|
||||
raw_wrmsr(MSR_AMD64_SEV_ES_GHCB, &m);
|
||||
}
|
||||
|
||||
#else
|
||||
|
|
|
|||
|
|
@ -26,9 +26,9 @@
|
|||
#include <asm/intel-family.h>
|
||||
#include <asm/processor-flags.h>
|
||||
#include <asm/msr-index.h>
|
||||
#include <asm/shared/msr.h>
|
||||
|
||||
#include "string.h"
|
||||
#include "msr.h"
|
||||
|
||||
static u32 err_flags[NCAPINTS];
|
||||
|
||||
|
|
@ -134,9 +134,9 @@ int check_cpu(int *cpu_level_ptr, int *req_level_ptr, u32 **err_flags_ptr)
|
|||
|
||||
struct msr m;
|
||||
|
||||
boot_rdmsr(MSR_K7_HWCR, &m);
|
||||
raw_rdmsr(MSR_K7_HWCR, &m);
|
||||
m.l &= ~(1 << 15);
|
||||
boot_wrmsr(MSR_K7_HWCR, &m);
|
||||
raw_wrmsr(MSR_K7_HWCR, &m);
|
||||
|
||||
get_cpuflags(); /* Make sure it really did something */
|
||||
err = check_cpuflags();
|
||||
|
|
@ -148,9 +148,9 @@ int check_cpu(int *cpu_level_ptr, int *req_level_ptr, u32 **err_flags_ptr)
|
|||
|
||||
struct msr m;
|
||||
|
||||
boot_rdmsr(MSR_VIA_FCR, &m);
|
||||
raw_rdmsr(MSR_VIA_FCR, &m);
|
||||
m.l |= (1 << 1) | (1 << 7);
|
||||
boot_wrmsr(MSR_VIA_FCR, &m);
|
||||
raw_wrmsr(MSR_VIA_FCR, &m);
|
||||
|
||||
set_bit(X86_FEATURE_CX8, cpu.flags);
|
||||
err = check_cpuflags();
|
||||
|
|
@ -160,14 +160,14 @@ int check_cpu(int *cpu_level_ptr, int *req_level_ptr, u32 **err_flags_ptr)
|
|||
struct msr m, m_tmp;
|
||||
u32 level = 1;
|
||||
|
||||
boot_rdmsr(0x80860004, &m);
|
||||
raw_rdmsr(0x80860004, &m);
|
||||
m_tmp = m;
|
||||
m_tmp.l = ~0;
|
||||
boot_wrmsr(0x80860004, &m_tmp);
|
||||
raw_wrmsr(0x80860004, &m_tmp);
|
||||
asm("cpuid"
|
||||
: "+a" (level), "=d" (cpu.flags[0])
|
||||
: : "ecx", "ebx");
|
||||
boot_wrmsr(0x80860004, &m);
|
||||
raw_wrmsr(0x80860004, &m);
|
||||
|
||||
err = check_cpuflags();
|
||||
} else if (err == 0x01 &&
|
||||
|
|
|
|||
|
|
@ -1,26 +0,0 @@
|
|||
/* SPDX-License-Identifier: GPL-2.0-only */
|
||||
/*
|
||||
* Helpers/definitions related to MSR access.
|
||||
*/
|
||||
|
||||
#ifndef BOOT_MSR_H
|
||||
#define BOOT_MSR_H
|
||||
|
||||
#include <asm/shared/msr.h>
|
||||
|
||||
/*
|
||||
* The kernel proper already defines rdmsr()/wrmsr(), but they are not for the
|
||||
* boot kernel since they rely on tracepoint/exception handling infrastructure
|
||||
* that's not available here.
|
||||
*/
|
||||
static inline void boot_rdmsr(unsigned int reg, struct msr *m)
|
||||
{
|
||||
asm volatile("rdmsr" : "=a" (m->l), "=d" (m->h) : "c" (reg));
|
||||
}
|
||||
|
||||
static inline void boot_wrmsr(unsigned int reg, const struct msr *m)
|
||||
{
|
||||
asm volatile("wrmsr" : : "c" (reg), "a"(m->l), "d" (m->h) : "memory");
|
||||
}
|
||||
|
||||
#endif /* BOOT_MSR_H */
|
||||
|
|
@ -12,7 +12,7 @@
|
|||
#include <asm/setup_data.h>
|
||||
|
||||
#ifndef __BOOT_COMPRESSED
|
||||
#define has_cpuflag(f) boot_cpu_has(f)
|
||||
#define has_cpuflag(f) cpu_feature_enabled(f)
|
||||
#else
|
||||
#undef WARN
|
||||
#define WARN(condition, format...) (!!(condition))
|
||||
|
|
|
|||
|
|
@ -352,7 +352,6 @@ static enum es_result vc_read_mem(struct es_em_ctxt *ctxt,
|
|||
|
||||
#define sev_printk(fmt, ...) printk(fmt, ##__VA_ARGS__)
|
||||
#define error(v)
|
||||
#define has_cpuflag(f) boot_cpu_has(f)
|
||||
|
||||
#include "vc-shared.c"
|
||||
|
||||
|
|
|
|||
|
|
@ -1,5 +1,9 @@
|
|||
// SPDX-License-Identifier: GPL-2.0
|
||||
|
||||
#ifndef __BOOT_COMPRESSED
|
||||
#define has_cpuflag(f) cpu_feature_enabled(f)
|
||||
#endif
|
||||
|
||||
static enum es_result vc_check_opcode_bytes(struct es_em_ctxt *ctxt,
|
||||
unsigned long exit_code)
|
||||
{
|
||||
|
|
@ -546,6 +550,13 @@ static enum es_result vc_handle_cpuid(struct ghcb *ghcb,
|
|||
/* xgetbv will cause #GP - use reset value for xcr0 */
|
||||
ghcb_set_xcr0(ghcb, 1);
|
||||
|
||||
if (has_cpuflag(X86_FEATURE_SHSTK) && regs->ax == 0xd && regs->cx == 1) {
|
||||
struct msr m;
|
||||
|
||||
raw_rdmsr(MSR_IA32_XSS, &m);
|
||||
ghcb_set_xss(ghcb, m.q);
|
||||
}
|
||||
|
||||
ret = sev_es_ghcb_hv_call(ghcb, ctxt, SVM_EXIT_CPUID, 0, 0);
|
||||
if (ret != ES_OK)
|
||||
return ret;
|
||||
|
|
|
|||
|
|
@ -12,4 +12,19 @@ struct msr {
|
|||
};
|
||||
};
|
||||
|
||||
/*
|
||||
* The kernel proper already defines rdmsr()/wrmsr(), but they are not for the
|
||||
* boot kernel since they rely on tracepoint/exception handling infrastructure
|
||||
* that's not available here.
|
||||
*/
|
||||
static inline void raw_rdmsr(unsigned int reg, struct msr *m)
|
||||
{
|
||||
asm volatile("rdmsr" : "=a" (m->l), "=d" (m->h) : "c" (reg));
|
||||
}
|
||||
|
||||
static inline void raw_wrmsr(unsigned int reg, const struct msr *m)
|
||||
{
|
||||
asm volatile("wrmsr" : : "c" (reg), "a"(m->l), "d" (m->h) : "memory");
|
||||
}
|
||||
|
||||
#endif /* _ASM_X86_SHARED_MSR_H */
|
||||
|
|
|
|||
|
|
@ -701,5 +701,6 @@ DEFINE_GHCB_ACCESSORS(sw_exit_info_1)
|
|||
DEFINE_GHCB_ACCESSORS(sw_exit_info_2)
|
||||
DEFINE_GHCB_ACCESSORS(sw_scratch)
|
||||
DEFINE_GHCB_ACCESSORS(xcr0)
|
||||
DEFINE_GHCB_ACCESSORS(xss)
|
||||
|
||||
#endif
|
||||
|
|
|
|||
|
|
@ -22,7 +22,7 @@
|
|||
#include <asm/setup.h>
|
||||
|
||||
#define debug_putstr(v) early_printk("%s", v)
|
||||
#define has_cpuflag(f) boot_cpu_has(f)
|
||||
#define has_cpuflag(f) cpu_feature_enabled(f)
|
||||
#define get_boot_seed() kaslr_offset()
|
||||
#endif
|
||||
|
||||
|
|
|
|||
|
|
@ -74,7 +74,7 @@ enum cc_attr {
|
|||
CC_ATTR_GUEST_UNROLL_STRING_IO,
|
||||
|
||||
/**
|
||||
* @CC_ATTR_SEV_SNP: Guest SNP is active.
|
||||
* @CC_ATTR_GUEST_SEV_SNP: Guest SNP is active.
|
||||
*
|
||||
* The platform/OS is running as a guest/virtual machine and actively
|
||||
* using AMD SEV-SNP features.
|
||||
|
|
|
|||
Loading…
Reference in New Issue
Block a user