Merge branches 'x86-cpu-for-linus' and 'x86-fpu-for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/tip/tip
Pull x86 cpu and fpu updates from Ingo Molnar: - math-emu fixes - CPUID updates - sanity-check RDRAND output to see whether the CPU at least pretends to produce random data - various unaligned-access across cachelines fixes in preparation of hardware level split-lock detection - fix MAXSMP constraints to not allow !CPUMASK_OFFSTACK kernels with larger than 512 NR_CPUS - misc FPU related cleanups * 'x86-cpu-for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/tip/tip: x86/cpu: Align the x86_capability array to size of unsigned long x86/cpu: Align cpu_caps_cleared and cpu_caps_set to unsigned long x86/umip: Make the comments vendor-agnostic x86/Kconfig: Rename UMIP config parameter x86/Kconfig: Enforce limit of 512 CPUs with MAXSMP and no CPUMASK_OFFSTACK x86/cpufeatures: Add feature bit RDPRU on AMD x86/math-emu: Limit MATH_EMULATION to 486SX compatibles x86/math-emu: Check __copy_from_user() result x86/rdrand: Sanity-check RDRAND output * 'x86-fpu-for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/tip/tip: x86/fpu: Use XFEATURE_FP/SSE enum values instead of hardcoded numbers x86/fpu: Shrink space allocated for xstate_comp_offsets x86/fpu: Update stale variable name in comment
This commit is contained in:
Коммит
a25bbc2644
|
@ -970,8 +970,8 @@ config NR_CPUS_RANGE_END
|
|||
config NR_CPUS_RANGE_END
|
||||
int
|
||||
depends on X86_64
|
||||
default 8192 if SMP && ( MAXSMP || CPUMASK_OFFSTACK)
|
||||
default 512 if SMP && (!MAXSMP && !CPUMASK_OFFSTACK)
|
||||
default 8192 if SMP && CPUMASK_OFFSTACK
|
||||
default 512 if SMP && !CPUMASK_OFFSTACK
|
||||
default 1 if !SMP
|
||||
|
||||
config NR_CPUS_DEFAULT
|
||||
|
@ -1721,7 +1721,7 @@ config X86_RESERVE_LOW
|
|||
config MATH_EMULATION
|
||||
bool
|
||||
depends on MODIFY_LDT_SYSCALL
|
||||
prompt "Math emulation" if X86_32
|
||||
prompt "Math emulation" if X86_32 && (M486SX || MELAN)
|
||||
---help---
|
||||
Linux can emulate a math coprocessor (used for floating point
|
||||
operations) if you don't have one. 486DX and Pentium processors have
|
||||
|
@ -1850,16 +1850,16 @@ config X86_SMAP
|
|||
|
||||
If unsure, say Y.
|
||||
|
||||
config X86_INTEL_UMIP
|
||||
config X86_UMIP
|
||||
def_bool y
|
||||
depends on CPU_SUP_INTEL
|
||||
prompt "Intel User Mode Instruction Prevention" if EXPERT
|
||||
depends on CPU_SUP_INTEL || CPU_SUP_AMD
|
||||
prompt "User Mode Instruction Prevention" if EXPERT
|
||||
---help---
|
||||
The User Mode Instruction Prevention (UMIP) is a security
|
||||
feature in newer Intel processors. If enabled, a general
|
||||
protection fault is issued if the SGDT, SLDT, SIDT, SMSW
|
||||
or STR instructions are executed in user mode. These instructions
|
||||
unnecessarily expose information about the hardware state.
|
||||
User Mode Instruction Prevention (UMIP) is a security feature in
|
||||
some x86 processors. If enabled, a general protection fault is
|
||||
issued if the SGDT, SLDT, SIDT, SMSW or STR instructions are
|
||||
executed in user mode. These instructions unnecessarily expose
|
||||
information about the hardware state.
|
||||
|
||||
The vast majority of applications do not use these instructions.
|
||||
For the very few that do, software emulation is provided in
|
||||
|
|
|
@ -50,12 +50,19 @@ choice
|
|||
See each option's help text for additional details. If you don't know
|
||||
what to do, choose "486".
|
||||
|
||||
config M486SX
|
||||
bool "486SX"
|
||||
depends on X86_32
|
||||
---help---
|
||||
Select this for an 486-class CPU without an FPU such as
|
||||
AMD/Cyrix/IBM/Intel SL/SLC/SLC2/SLC3/SX/SX2 and UMC U5S.
|
||||
|
||||
config M486
|
||||
bool "486"
|
||||
bool "486DX"
|
||||
depends on X86_32
|
||||
---help---
|
||||
Select this for an 486-class CPU such as AMD/Cyrix/IBM/Intel
|
||||
486DX/DX2/DX4 or SL/SLC/SLC2/SLC3/SX/SX2 and UMC U5D or U5S.
|
||||
486DX/DX2/DX4 and UMC U5D.
|
||||
|
||||
config M586
|
||||
bool "586/K5/5x86/6x86/6x86MX"
|
||||
|
@ -312,20 +319,20 @@ config X86_L1_CACHE_SHIFT
|
|||
int
|
||||
default "7" if MPENTIUM4 || MPSC
|
||||
default "6" if MK7 || MK8 || MPENTIUMM || MCORE2 || MATOM || MVIAC7 || X86_GENERIC || GENERIC_CPU
|
||||
default "4" if MELAN || M486 || MGEODEGX1
|
||||
default "4" if MELAN || M486SX || M486 || MGEODEGX1
|
||||
default "5" if MWINCHIP3D || MWINCHIPC6 || MCRUSOE || MEFFICEON || MCYRIXIII || MK6 || MPENTIUMIII || MPENTIUMII || M686 || M586MMX || M586TSC || M586 || MVIAC3_2 || MGEODE_LX
|
||||
|
||||
config X86_F00F_BUG
|
||||
def_bool y
|
||||
depends on M586MMX || M586TSC || M586 || M486
|
||||
depends on M586MMX || M586TSC || M586 || M486SX || M486
|
||||
|
||||
config X86_INVD_BUG
|
||||
def_bool y
|
||||
depends on M486
|
||||
depends on M486SX || M486
|
||||
|
||||
config X86_ALIGNMENT_16
|
||||
def_bool y
|
||||
depends on MWINCHIP3D || MWINCHIPC6 || MCYRIXIII || MELAN || MK6 || M586MMX || M586TSC || M586 || M486 || MVIAC3_2 || MGEODEGX1
|
||||
depends on MWINCHIP3D || MWINCHIPC6 || MCYRIXIII || MELAN || MK6 || M586MMX || M586TSC || M586 || M486SX || M486 || MVIAC3_2 || MGEODEGX1
|
||||
|
||||
config X86_INTEL_USERCOPY
|
||||
def_bool y
|
||||
|
@ -378,7 +385,7 @@ config X86_MINIMUM_CPU_FAMILY
|
|||
|
||||
config X86_DEBUGCTLMSR
|
||||
def_bool y
|
||||
depends on !(MK6 || MWINCHIPC6 || MWINCHIP3D || MCYRIXIII || M586MMX || M586TSC || M586 || M486) && !UML
|
||||
depends on !(MK6 || MWINCHIPC6 || MWINCHIP3D || MCYRIXIII || M586MMX || M586TSC || M586 || M486SX || M486) && !UML
|
||||
|
||||
menuconfig PROCESSOR_SELECT
|
||||
bool "Supported processor vendors" if EXPERT
|
||||
|
@ -402,7 +409,7 @@ config CPU_SUP_INTEL
|
|||
config CPU_SUP_CYRIX_32
|
||||
default y
|
||||
bool "Support Cyrix processors" if PROCESSOR_SELECT
|
||||
depends on M486 || M586 || M586TSC || M586MMX || (EXPERT && !64BIT)
|
||||
depends on M486SX || M486 || M586 || M586TSC || M586MMX || (EXPERT && !64BIT)
|
||||
---help---
|
||||
This enables detection, tunings and quirks for Cyrix processors
|
||||
|
||||
|
@ -470,7 +477,7 @@ config CPU_SUP_TRANSMETA_32
|
|||
config CPU_SUP_UMC_32
|
||||
default y
|
||||
bool "Support UMC processors" if PROCESSOR_SELECT
|
||||
depends on M486 || (EXPERT && !64BIT)
|
||||
depends on M486SX || M486 || (EXPERT && !64BIT)
|
||||
---help---
|
||||
This enables detection, tunings and quirks for UMC processors
|
||||
|
||||
|
|
|
@ -10,6 +10,7 @@ else
|
|||
tune = $(call cc-option,-mcpu=$(1),$(2))
|
||||
endif
|
||||
|
||||
cflags-$(CONFIG_M486SX) += -march=i486
|
||||
cflags-$(CONFIG_M486) += -march=i486
|
||||
cflags-$(CONFIG_M586) += -march=i586
|
||||
cflags-$(CONFIG_M586TSC) += -march=i586
|
||||
|
|
|
@ -292,6 +292,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_RDPRU (13*32+ 4) /* Read processor register at user level */
|
||||
#define X86_FEATURE_WBNOINVD (13*32+ 9) /* WBNOINVD instruction */
|
||||
#define X86_FEATURE_AMD_IBPB (13*32+12) /* "" Indirect Branch Prediction Barrier */
|
||||
#define X86_FEATURE_AMD_IBRS (13*32+14) /* "" Indirect Branch Restricted Speculation */
|
||||
|
|
|
@ -22,7 +22,7 @@
|
|||
# define DISABLE_SMAP (1<<(X86_FEATURE_SMAP & 31))
|
||||
#endif
|
||||
|
||||
#ifdef CONFIG_X86_INTEL_UMIP
|
||||
#ifdef CONFIG_X86_UMIP
|
||||
# define DISABLE_UMIP 0
|
||||
#else
|
||||
# define DISABLE_UMIP (1<<(X86_FEATURE_UMIP & 31))
|
||||
|
|
|
@ -15,6 +15,8 @@ struct mod_arch_specific {
|
|||
|
||||
#ifdef CONFIG_X86_64
|
||||
/* X86_64 does not define MODULE_PROC_FAMILY */
|
||||
#elif defined CONFIG_M486SX
|
||||
#define MODULE_PROC_FAMILY "486SX "
|
||||
#elif defined CONFIG_M486
|
||||
#define MODULE_PROC_FAMILY "486 "
|
||||
#elif defined CONFIG_M586
|
||||
|
|
|
@ -93,7 +93,15 @@ struct cpuinfo_x86 {
|
|||
__u32 extended_cpuid_level;
|
||||
/* Maximum supported CPUID level, -1=no CPUID: */
|
||||
int cpuid_level;
|
||||
__u32 x86_capability[NCAPINTS + NBUGINTS];
|
||||
/*
|
||||
* Align to size of unsigned long because the x86_capability array
|
||||
* is passed to bitops which require the alignment. Use unnamed
|
||||
* union to enforce the array is aligned to size of unsigned long.
|
||||
*/
|
||||
union {
|
||||
__u32 x86_capability[NCAPINTS + NBUGINTS];
|
||||
unsigned long x86_capability_alignment;
|
||||
};
|
||||
char x86_vendor_id[16];
|
||||
char x86_model_id[64];
|
||||
/* in KB - valid for CPUS which support this call: */
|
||||
|
|
|
@ -4,9 +4,9 @@
|
|||
#include <linux/types.h>
|
||||
#include <asm/ptrace.h>
|
||||
|
||||
#ifdef CONFIG_X86_INTEL_UMIP
|
||||
#ifdef CONFIG_X86_UMIP
|
||||
bool fixup_umip_exception(struct pt_regs *regs);
|
||||
#else
|
||||
static inline bool fixup_umip_exception(struct pt_regs *regs) { return false; }
|
||||
#endif /* CONFIG_X86_INTEL_UMIP */
|
||||
#endif /* CONFIG_X86_UMIP */
|
||||
#endif /* _ASM_X86_UMIP_H */
|
||||
|
|
|
@ -134,7 +134,7 @@ obj-$(CONFIG_EFI) += sysfb_efi.o
|
|||
obj-$(CONFIG_PERF_EVENTS) += perf_regs.o
|
||||
obj-$(CONFIG_TRACING) += tracepoint.o
|
||||
obj-$(CONFIG_SCHED_MC_PRIO) += itmt.o
|
||||
obj-$(CONFIG_X86_INTEL_UMIP) += umip.o
|
||||
obj-$(CONFIG_X86_UMIP) += umip.o
|
||||
|
||||
obj-$(CONFIG_UNWINDER_ORC) += unwind_orc.o
|
||||
obj-$(CONFIG_UNWINDER_FRAME_POINTER) += unwind_frame.o
|
||||
|
|
|
@ -565,8 +565,9 @@ static const char *table_lookup_model(struct cpuinfo_x86 *c)
|
|||
return NULL; /* Not found */
|
||||
}
|
||||
|
||||
__u32 cpu_caps_cleared[NCAPINTS + NBUGINTS];
|
||||
__u32 cpu_caps_set[NCAPINTS + NBUGINTS];
|
||||
/* Aligned to unsigned long to avoid split lock in atomic bitmap ops */
|
||||
__u32 cpu_caps_cleared[NCAPINTS + NBUGINTS] __aligned(sizeof(unsigned long));
|
||||
__u32 cpu_caps_set[NCAPINTS + NBUGINTS] __aligned(sizeof(unsigned long));
|
||||
|
||||
void load_percpu_segment(int cpu)
|
||||
{
|
||||
|
|
|
@ -29,7 +29,8 @@ __setup("nordrand", x86_rdrand_setup);
|
|||
#ifdef CONFIG_ARCH_RANDOM
|
||||
void x86_init_rdrand(struct cpuinfo_x86 *c)
|
||||
{
|
||||
unsigned long tmp;
|
||||
unsigned int changed = 0;
|
||||
unsigned long tmp, prev;
|
||||
int i;
|
||||
|
||||
if (!cpu_has(c, X86_FEATURE_RDRAND))
|
||||
|
@ -42,5 +43,24 @@ void x86_init_rdrand(struct cpuinfo_x86 *c)
|
|||
return;
|
||||
}
|
||||
}
|
||||
|
||||
/*
|
||||
* Stupid sanity-check whether RDRAND does *actually* generate
|
||||
* some at least random-looking data.
|
||||
*/
|
||||
prev = tmp;
|
||||
for (i = 0; i < SANITY_CHECK_LOOPS; i++) {
|
||||
if (rdrand_long(&tmp)) {
|
||||
if (prev != tmp)
|
||||
changed++;
|
||||
|
||||
prev = tmp;
|
||||
}
|
||||
}
|
||||
|
||||
if (WARN_ON_ONCE(!changed))
|
||||
pr_emerg(
|
||||
"RDRAND gives funky smelling output, might consider not using it by booting with \"nordrand\"");
|
||||
|
||||
}
|
||||
#endif
|
||||
|
|
|
@ -60,7 +60,7 @@ u64 xfeatures_mask __read_mostly;
|
|||
|
||||
static unsigned int xstate_offsets[XFEATURE_MAX] = { [ 0 ... XFEATURE_MAX - 1] = -1};
|
||||
static unsigned int xstate_sizes[XFEATURE_MAX] = { [ 0 ... XFEATURE_MAX - 1] = -1};
|
||||
static unsigned int xstate_comp_offsets[sizeof(xfeatures_mask)*8];
|
||||
static unsigned int xstate_comp_offsets[XFEATURE_MAX] = { [ 0 ... XFEATURE_MAX - 1] = -1};
|
||||
|
||||
/*
|
||||
* The XSAVE area of kernel can be in standard or compacted format;
|
||||
|
@ -254,10 +254,13 @@ static void __init setup_xstate_features(void)
|
|||
* in the fixed offsets in the xsave area in either compacted form
|
||||
* or standard form.
|
||||
*/
|
||||
xstate_offsets[0] = 0;
|
||||
xstate_sizes[0] = offsetof(struct fxregs_state, xmm_space);
|
||||
xstate_offsets[1] = xstate_sizes[0];
|
||||
xstate_sizes[1] = FIELD_SIZEOF(struct fxregs_state, xmm_space);
|
||||
xstate_offsets[XFEATURE_FP] = 0;
|
||||
xstate_sizes[XFEATURE_FP] = offsetof(struct fxregs_state,
|
||||
xmm_space);
|
||||
|
||||
xstate_offsets[XFEATURE_SSE] = xstate_sizes[XFEATURE_FP];
|
||||
xstate_sizes[XFEATURE_SSE] = FIELD_SIZEOF(struct fxregs_state,
|
||||
xmm_space);
|
||||
|
||||
for (i = FIRST_EXTENDED_XFEATURE; i < XFEATURE_MAX; i++) {
|
||||
if (!xfeature_enabled(i))
|
||||
|
@ -342,7 +345,7 @@ static int xfeature_is_aligned(int xfeature_nr)
|
|||
*/
|
||||
static void __init setup_xstate_comp(void)
|
||||
{
|
||||
unsigned int xstate_comp_sizes[sizeof(xfeatures_mask)*8];
|
||||
unsigned int xstate_comp_sizes[XFEATURE_MAX];
|
||||
int i;
|
||||
|
||||
/*
|
||||
|
@ -350,8 +353,9 @@ static void __init setup_xstate_comp(void)
|
|||
* in the fixed offsets in the xsave area in either compacted form
|
||||
* or standard form.
|
||||
*/
|
||||
xstate_comp_offsets[0] = 0;
|
||||
xstate_comp_offsets[1] = offsetof(struct fxregs_state, xmm_space);
|
||||
xstate_comp_offsets[XFEATURE_FP] = 0;
|
||||
xstate_comp_offsets[XFEATURE_SSE] = offsetof(struct fxregs_state,
|
||||
xmm_space);
|
||||
|
||||
if (!boot_cpu_has(X86_FEATURE_XSAVES)) {
|
||||
for (i = FIRST_EXTENDED_XFEATURE; i < XFEATURE_MAX; i++) {
|
||||
|
@ -840,7 +844,7 @@ void *get_xsave_addr(struct xregs_state *xsave, int xfeature_nr)
|
|||
|
||||
/*
|
||||
* We should not ever be requesting features that we
|
||||
* have not enabled. Remember that pcntxt_mask is
|
||||
* have not enabled. Remember that xfeatures_mask is
|
||||
* what we write to the XCR0 register.
|
||||
*/
|
||||
WARN_ONCE(!(xfeatures_mask & BIT_ULL(xfeature_nr)),
|
||||
|
|
|
@ -1,6 +1,6 @@
|
|||
/*
|
||||
* umip.c Emulation for instruction protected by the Intel User-Mode
|
||||
* Instruction Prevention feature
|
||||
* umip.c Emulation for instruction protected by the User-Mode Instruction
|
||||
* Prevention feature
|
||||
*
|
||||
* Copyright (c) 2017, Intel Corporation.
|
||||
* Ricardo Neri <ricardo.neri-calderon@linux.intel.com>
|
||||
|
@ -18,10 +18,10 @@
|
|||
|
||||
/** DOC: Emulation for User-Mode Instruction Prevention (UMIP)
|
||||
*
|
||||
* The feature User-Mode Instruction Prevention present in recent Intel
|
||||
* processor prevents a group of instructions (SGDT, SIDT, SLDT, SMSW and STR)
|
||||
* from being executed with CPL > 0. Otherwise, a general protection fault is
|
||||
* issued.
|
||||
* User-Mode Instruction Prevention is a security feature present in recent
|
||||
* x86 processors that, when enabled, prevents a group of instructions (SGDT,
|
||||
* SIDT, SLDT, SMSW and STR) from being run in user mode by issuing a general
|
||||
* protection fault if the instruction is executed with CPL > 0.
|
||||
*
|
||||
* Rather than relaying to the user space the general protection fault caused by
|
||||
* the UMIP-protected instructions (in the form of a SIGSEGV signal), it can be
|
||||
|
|
|
@ -107,6 +107,8 @@ static inline bool seg_writable(struct desc_struct *d)
|
|||
#define FPU_access_ok(y,z) if ( !access_ok(y,z) ) \
|
||||
math_abort(FPU_info,SIGSEGV)
|
||||
#define FPU_abort math_abort(FPU_info, SIGSEGV)
|
||||
#define FPU_copy_from_user(to, from, n) \
|
||||
do { if (copy_from_user(to, from, n)) FPU_abort; } while (0)
|
||||
|
||||
#undef FPU_IGNORE_CODE_SEGV
|
||||
#ifdef FPU_IGNORE_CODE_SEGV
|
||||
|
@ -122,7 +124,7 @@ static inline bool seg_writable(struct desc_struct *d)
|
|||
#define FPU_code_access_ok(z) FPU_access_ok((void __user *)FPU_EIP,z)
|
||||
#endif
|
||||
|
||||
#define FPU_get_user(x,y) get_user((x),(y))
|
||||
#define FPU_put_user(x,y) put_user((x),(y))
|
||||
#define FPU_get_user(x,y) do { if (get_user((x),(y))) FPU_abort; } while (0)
|
||||
#define FPU_put_user(x,y) do { if (put_user((x),(y))) FPU_abort; } while (0)
|
||||
|
||||
#endif
|
||||
|
|
|
@ -85,7 +85,7 @@ int FPU_load_extended(long double __user *s, int stnr)
|
|||
|
||||
RE_ENTRANT_CHECK_OFF;
|
||||
FPU_access_ok(s, 10);
|
||||
__copy_from_user(sti_ptr, s, 10);
|
||||
FPU_copy_from_user(sti_ptr, s, 10);
|
||||
RE_ENTRANT_CHECK_ON;
|
||||
|
||||
return FPU_tagof(sti_ptr);
|
||||
|
@ -1126,9 +1126,9 @@ void frstor(fpu_addr_modes addr_modes, u_char __user *data_address)
|
|||
/* Copy all registers in stack order. */
|
||||
RE_ENTRANT_CHECK_OFF;
|
||||
FPU_access_ok(s, 80);
|
||||
__copy_from_user(register_base + offset, s, other);
|
||||
FPU_copy_from_user(register_base + offset, s, other);
|
||||
if (offset)
|
||||
__copy_from_user(register_base, s + other, offset);
|
||||
FPU_copy_from_user(register_base, s + other, offset);
|
||||
RE_ENTRANT_CHECK_ON;
|
||||
|
||||
for (i = 0; i < 8; i++) {
|
||||
|
|
|
@ -22,7 +22,7 @@
|
|||
# define DISABLE_SMAP (1<<(X86_FEATURE_SMAP & 31))
|
||||
#endif
|
||||
|
||||
#ifdef CONFIG_X86_INTEL_UMIP
|
||||
#ifdef CONFIG_X86_UMIP
|
||||
# define DISABLE_UMIP 0
|
||||
#else
|
||||
# define DISABLE_UMIP (1<<(X86_FEATURE_UMIP & 31))
|
||||
|
|
Загрузка…
Ссылка в новой задаче