From: Thomas Gleixner Signed-off-by: Thomas Gleixner Signed-off-by: Peter Zijlstra (Intel) --- arch/x86/include/asm/cpufeatures.h | 4 +++- arch/x86/include/asm/msr-index.h | 3 +++ arch/x86/include/asm/nospec-branch.h | 9 +++++++++ arch/x86/kernel/cpu/bugs.c | 2 ++ arch/x86/kernel/cpu/specctrl.c | 9 +++++++++ 5 files changed, 26 insertions(+), 1 deletion(-) --- a/arch/x86/include/asm/cpufeatures.h +++ b/arch/x86/include/asm/cpufeatures.h @@ -212,8 +212,9 @@ #define X86_FEATURE_MBA ( 7*32+18) /* Memory Bandwidth Allocation */ #define X86_FEATURE_RSB_CTXSW ( 7*32+19) /* Fill RSB on context switches */ -#define X86_FEATURE_SPEC_CTRL ( 7*32+20) /* Speculation Control */ +#define X86_FEATURE_SPEC_CTRL ( 7*32+20) /* Speculation Control - Intel only */ #define X86_FEATURE_IBRS ( 7*32+21) /* Indirect Branch Restricted Speculation */ +#define X86_FEATURE_IBPB ( 7*32+22) /* Indirect Branch Prediction Barrier */ /* Virtualization flags: Linux defined, word 8 */ #define X86_FEATURE_TPR_SHADOW ( 8*32+ 0) /* Intel TPR Shadow */ @@ -273,6 +274,7 @@ #define X86_FEATURE_CLZERO (13*32+ 0) /* CLZERO instruction */ #define X86_FEATURE_IRPERF (13*32+ 1) /* Instructions Retired Count */ #define X86_FEATURE_XSAVEERPTR (13*32+ 2) /* Always save/restore FP error pointers */ +#define X86_FEATURE_AMD_IBPB (13*32+12) /* Indirect Branch Prediction Barrier support */ /* Thermal and Power Management Leaf, CPUID level 0x00000006 (EAX), word 14 */ #define X86_FEATURE_DTHERM (14*32+ 0) /* Digital Thermal Sensor */ --- a/arch/x86/include/asm/msr-index.h +++ b/arch/x86/include/asm/msr-index.h @@ -46,6 +46,9 @@ #define SPEC_CTRL_DISABLE_IBRS (0 << 0) #define SPEC_CTRL_ENABLE_IBRS (1 << 0) +#define MSR_IA32_PRED_CMD 0x00000049 +#define PRED_CMD_IBPB (1 << 0) + #define MSR_IA32_PERFCTR0 0x000000c1 #define MSR_IA32_PERFCTR1 0x000000c2 #define MSR_FSB_FREQ 0x000000cd --- a/arch/x86/include/asm/nospec-branch.h +++ b/arch/x86/include/asm/nospec-branch.h @@ -231,5 +231,14 @@ static inline void restart_indirect_bran if (static_cpu_has(X86_FEATURE_IBRS)) native_wrmsrl(MSR_IA32_SPEC_CTRL, SPEC_CTRL_DISABLE_IBRS); } + +void specctrl_init_ibpb(void); + +static inline void indirect_branch_prediction_barrier(void) +{ + if (static_cpu_has(X86_FEATURE_IBPB)) + native_wrmsrl(MSR_IA32_PRED_CMD, PRED_CMD_IBPB); +} + #endif /* __ASSEMBLY__ */ #endif /* __NOSPEC_BRANCH_H__ */ --- a/arch/x86/kernel/cpu/bugs.c +++ b/arch/x86/kernel/cpu/bugs.c @@ -271,6 +271,8 @@ static void __init spectre_v2_select_mit setup_force_cpu_cap(X86_FEATURE_RSB_CTXSW); pr_info("Filling RSB on context switch\n"); } + /* Initialize Indirect Branch Prediction Barrier if supported */ + specctrl_init_ibpb(); } #undef pr_fmt --- a/arch/x86/kernel/cpu/specctrl.c +++ b/arch/x86/kernel/cpu/specctrl.c @@ -30,3 +30,12 @@ bool __init specctrl_cond_enable_ibrs(bo specctrl_enable_ibrs(); return true; } + +void __init specctrl_init_ibpb(void) +{ + if (!boot_cpu_has(X86_FEATURE_SPEC_CTRL) && + !boot_cpu_has(X86_FEATURE_AMD_IBPB)) + return; + + setup_force_cpu_cap(X86_FEATURE_IBPB); +}