Commit 73270c1f authored by Xin Li (Intel)'s avatar Xin Li (Intel) Committed by Thomas Gleixner

x86/fred: Move FRED RSP initialization into a separate function

To enable FRED earlier, move the RSP initialization out of
cpu_init_fred_exceptions() into cpu_init_fred_rsps().

This is required as the FRED RSP initialization depends on the availability
of the CPU entry areas which are set up late in trap_init(),

No functional change intended. Marked with Fixes as it's a depedency for
the real fix.

Fixes: 14619d91 ("x86/fred: FRED entry/exit and dispatch code")
Signed-off-by: default avatarXin Li (Intel) <xin@zytor.com>
Signed-off-by: default avatarThomas Gleixner <tglx@linutronix.de>
Link: https://lore.kernel.org/all/20240709154048.3543361-3-xin@zytor.com
parent 989b5cfa
...@@ -84,11 +84,13 @@ static __always_inline void fred_entry_from_kvm(unsigned int type, unsigned int ...@@ -84,11 +84,13 @@ static __always_inline void fred_entry_from_kvm(unsigned int type, unsigned int
} }
void cpu_init_fred_exceptions(void); void cpu_init_fred_exceptions(void);
void cpu_init_fred_rsps(void);
void fred_complete_exception_setup(void); void fred_complete_exception_setup(void);
#else /* CONFIG_X86_FRED */ #else /* CONFIG_X86_FRED */
static __always_inline unsigned long fred_event_data(struct pt_regs *regs) { return 0; } static __always_inline unsigned long fred_event_data(struct pt_regs *regs) { return 0; }
static inline void cpu_init_fred_exceptions(void) { } static inline void cpu_init_fred_exceptions(void) { }
static inline void cpu_init_fred_rsps(void) { }
static inline void fred_complete_exception_setup(void) { } static inline void fred_complete_exception_setup(void) { }
static __always_inline void fred_entry_from_kvm(unsigned int type, unsigned int vector) { } static __always_inline void fred_entry_from_kvm(unsigned int type, unsigned int vector) { }
#endif /* CONFIG_X86_FRED */ #endif /* CONFIG_X86_FRED */
......
...@@ -2195,10 +2195,12 @@ void cpu_init_exception_handling(void) ...@@ -2195,10 +2195,12 @@ void cpu_init_exception_handling(void)
/* GHCB needs to be setup to handle #VC. */ /* GHCB needs to be setup to handle #VC. */
setup_ghcb(); setup_ghcb();
if (cpu_feature_enabled(X86_FEATURE_FRED)) if (cpu_feature_enabled(X86_FEATURE_FRED)) {
cpu_init_fred_exceptions(); cpu_init_fred_exceptions();
else cpu_init_fred_rsps();
} else {
load_current_idt(); load_current_idt();
}
} }
/* /*
......
...@@ -32,6 +32,25 @@ void cpu_init_fred_exceptions(void) ...@@ -32,6 +32,25 @@ void cpu_init_fred_exceptions(void)
FRED_CONFIG_INT_STKLVL(0) | FRED_CONFIG_INT_STKLVL(0) |
FRED_CONFIG_ENTRYPOINT(asm_fred_entrypoint_user)); FRED_CONFIG_ENTRYPOINT(asm_fred_entrypoint_user));
wrmsrl(MSR_IA32_FRED_STKLVLS, 0);
wrmsrl(MSR_IA32_FRED_RSP0, 0);
wrmsrl(MSR_IA32_FRED_RSP1, 0);
wrmsrl(MSR_IA32_FRED_RSP2, 0);
wrmsrl(MSR_IA32_FRED_RSP3, 0);
/* Enable FRED */
cr4_set_bits(X86_CR4_FRED);
/* Any further IDT use is a bug */
idt_invalidate();
/* Use int $0x80 for 32-bit system calls in FRED mode */
setup_clear_cpu_cap(X86_FEATURE_SYSENTER32);
setup_clear_cpu_cap(X86_FEATURE_SYSCALL32);
}
/* Must be called after setup_cpu_entry_areas() */
void cpu_init_fred_rsps(void)
{
/* /*
* The purpose of separate stacks for NMI, #DB and #MC *in the kernel* * The purpose of separate stacks for NMI, #DB and #MC *in the kernel*
* (remember that user space faults are always taken on stack level 0) * (remember that user space faults are always taken on stack level 0)
...@@ -47,13 +66,4 @@ void cpu_init_fred_exceptions(void) ...@@ -47,13 +66,4 @@ void cpu_init_fred_exceptions(void)
wrmsrl(MSR_IA32_FRED_RSP1, __this_cpu_ist_top_va(DB)); wrmsrl(MSR_IA32_FRED_RSP1, __this_cpu_ist_top_va(DB));
wrmsrl(MSR_IA32_FRED_RSP2, __this_cpu_ist_top_va(NMI)); wrmsrl(MSR_IA32_FRED_RSP2, __this_cpu_ist_top_va(NMI));
wrmsrl(MSR_IA32_FRED_RSP3, __this_cpu_ist_top_va(DF)); wrmsrl(MSR_IA32_FRED_RSP3, __this_cpu_ist_top_va(DF));
/* Enable FRED */
cr4_set_bits(X86_CR4_FRED);
/* Any further IDT use is a bug */
idt_invalidate();
/* Use int $0x80 for 32-bit system calls in FRED mode */
setup_clear_cpu_cap(X86_FEATURE_SYSENTER32);
setup_clear_cpu_cap(X86_FEATURE_SYSCALL32);
} }
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment