Linux kernel mirror (for testing) git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel os linux
1
fork

Configure Feed

Select the types of activity you want to include in your feed.

Merge branch 'x86-urgent-for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/tip/tip

Pull x86 fixes from Ingo Molnar:
"This fixes 3 FPU handling related bugs, an EFI boot crash and a
runtime warning.

The EFI fix arrived late but I didn't want to delay it to after v4.5
because the effects are pretty bad for the systems that are affected
by it"

[ Actually, I don't think the EFI fix really matters yet, because we
haven't switched to the separate EFI page tables in mainline yet ]

* 'x86-urgent-for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/tip/tip:
x86/efi: Fix boot crash by always mapping boot service regions into new EFI page tables
x86/fpu: Fix eager-FPU handling on legacy FPU machines
x86/delay: Avoid preemptible context checks in delay_mwaitx()
x86/fpu: Revert ("x86/fpu: Disable AVX when eagerfpu is off")
x86/fpu: Fix 'no387' regression

+79 -37
+4 -5
arch/x86/include/asm/fpu/xstate.h
··· 20 20 21 21 /* Supported features which support lazy state saving */ 22 22 #define XFEATURE_MASK_LAZY (XFEATURE_MASK_FP | \ 23 - XFEATURE_MASK_SSE) 24 - 25 - /* Supported features which require eager state saving */ 26 - #define XFEATURE_MASK_EAGER (XFEATURE_MASK_BNDREGS | \ 27 - XFEATURE_MASK_BNDCSR | \ 23 + XFEATURE_MASK_SSE | \ 28 24 XFEATURE_MASK_YMM | \ 29 25 XFEATURE_MASK_OPMASK | \ 30 26 XFEATURE_MASK_ZMM_Hi256 | \ 31 27 XFEATURE_MASK_Hi16_ZMM) 28 + 29 + /* Supported features which require eager state saving */ 30 + #define XFEATURE_MASK_EAGER (XFEATURE_MASK_BNDREGS | XFEATURE_MASK_BNDCSR) 32 31 33 32 /* All currently supported features */ 34 33 #define XCNTXT_MASK (XFEATURE_MASK_LAZY | XFEATURE_MASK_EAGER)
+3 -1
arch/x86/kernel/fpu/core.c
··· 409 409 { 410 410 if (use_xsave()) 411 411 copy_kernel_to_xregs(&init_fpstate.xsave, -1); 412 - else 412 + else if (static_cpu_has(X86_FEATURE_FXSR)) 413 413 copy_kernel_to_fxregs(&init_fpstate.fxsave); 414 + else 415 + copy_kernel_to_fregs(&init_fpstate.fsave); 414 416 } 415 417 416 418 /*
+9 -13
arch/x86/kernel/fpu/init.c
··· 78 78 cr0 &= ~(X86_CR0_TS | X86_CR0_EM); 79 79 write_cr0(cr0); 80 80 81 - asm volatile("fninit ; fnstsw %0 ; fnstcw %1" 82 - : "+m" (fsw), "+m" (fcw)); 81 + if (!test_bit(X86_FEATURE_FPU, (unsigned long *)cpu_caps_cleared)) { 82 + asm volatile("fninit ; fnstsw %0 ; fnstcw %1" 83 + : "+m" (fsw), "+m" (fcw)); 83 84 84 - if (fsw == 0 && (fcw & 0x103f) == 0x003f) 85 - set_cpu_cap(c, X86_FEATURE_FPU); 86 - else 87 - clear_cpu_cap(c, X86_FEATURE_FPU); 85 + if (fsw == 0 && (fcw & 0x103f) == 0x003f) 86 + set_cpu_cap(c, X86_FEATURE_FPU); 87 + else 88 + clear_cpu_cap(c, X86_FEATURE_FPU); 89 + } 88 90 89 91 #ifndef CONFIG_MATH_EMULATION 90 92 if (!cpu_has_fpu) { ··· 134 132 * Set up the legacy init FPU context. (xstate init might overwrite this 135 133 * with a more modern format, if the CPU supports it.) 136 134 */ 137 - fpstate_init_fxstate(&init_fpstate.fxsave); 135 + fpstate_init(&init_fpstate); 138 136 139 137 fpu__init_system_mxcsr(); 140 138 } ··· 302 300 static void __init fpu__clear_eager_fpu_features(void) 303 301 { 304 302 setup_clear_cpu_cap(X86_FEATURE_MPX); 305 - setup_clear_cpu_cap(X86_FEATURE_AVX); 306 - setup_clear_cpu_cap(X86_FEATURE_AVX2); 307 - setup_clear_cpu_cap(X86_FEATURE_AVX512F); 308 - setup_clear_cpu_cap(X86_FEATURE_AVX512PF); 309 - setup_clear_cpu_cap(X86_FEATURE_AVX512ER); 310 - setup_clear_cpu_cap(X86_FEATURE_AVX512CD); 311 303 } 312 304 313 305 /*
+1 -1
arch/x86/lib/delay.c
··· 102 102 * Use cpu_tss as a cacheline-aligned, seldomly 103 103 * accessed per-cpu variable as the monitor target. 104 104 */ 105 - __monitorx(this_cpu_ptr(&cpu_tss), 0, 0); 105 + __monitorx(raw_cpu_ptr(&cpu_tss), 0, 0); 106 106 107 107 /* 108 108 * AMD, like Intel, supports the EAX hint and EAX=0xf
+62 -17
arch/x86/platform/efi/quirks.c
··· 131 131 EXPORT_SYMBOL_GPL(efi_query_variable_store); 132 132 133 133 /* 134 + * Helper function for efi_reserve_boot_services() to figure out if we 135 + * can free regions in efi_free_boot_services(). 136 + * 137 + * Use this function to ensure we do not free regions owned by somebody 138 + * else. We must only reserve (and then free) regions: 139 + * 140 + * - Not within any part of the kernel 141 + * - Not the BIOS reserved area (E820_RESERVED, E820_NVS, etc) 142 + */ 143 + static bool can_free_region(u64 start, u64 size) 144 + { 145 + if (start + size > __pa_symbol(_text) && start <= __pa_symbol(_end)) 146 + return false; 147 + 148 + if (!e820_all_mapped(start, start+size, E820_RAM)) 149 + return false; 150 + 151 + return true; 152 + } 153 + 154 + /* 134 155 * The UEFI specification makes it clear that the operating system is free to do 135 156 * whatever it wants with boot services code after ExitBootServices() has been 136 157 * called. Ignoring this recommendation a significant bunch of EFI implementations ··· 168 147 efi_memory_desc_t *md = p; 169 148 u64 start = md->phys_addr; 170 149 u64 size = md->num_pages << EFI_PAGE_SHIFT; 150 + bool already_reserved; 171 151 172 152 if (md->type != EFI_BOOT_SERVICES_CODE && 173 153 md->type != EFI_BOOT_SERVICES_DATA) 174 154 continue; 175 - /* Only reserve where possible: 176 - * - Not within any already allocated areas 177 - * - Not over any memory area (really needed, if above?) 178 - * - Not within any part of the kernel 179 - * - Not the bios reserved area 180 - */ 181 - if ((start + size > __pa_symbol(_text) 182 - && start <= __pa_symbol(_end)) || 183 - !e820_all_mapped(start, start+size, E820_RAM) || 184 - memblock_is_region_reserved(start, size)) { 185 - /* Could not reserve, skip it */ 186 - md->num_pages = 0; 187 - memblock_dbg("Could not reserve boot range [0x%010llx-0x%010llx]\n", 188 - start, start+size-1); 189 - } else 155 + 156 + already_reserved = memblock_is_region_reserved(start, size); 157 + 158 + /* 159 + * Because the following memblock_reserve() is paired 160 + * with free_bootmem_late() for this region in 161 + * efi_free_boot_services(), we must be extremely 162 + * careful not to reserve, and subsequently free, 163 + * critical regions of memory (like the kernel image) or 164 + * those regions that somebody else has already 165 + * reserved. 166 + * 167 + * A good example of a critical region that must not be 168 + * freed is page zero (first 4Kb of memory), which may 169 + * contain boot services code/data but is marked 170 + * E820_RESERVED by trim_bios_range(). 171 + */ 172 + if (!already_reserved) { 190 173 memblock_reserve(start, size); 174 + 175 + /* 176 + * If we are the first to reserve the region, no 177 + * one else cares about it. We own it and can 178 + * free it later. 179 + */ 180 + if (can_free_region(start, size)) 181 + continue; 182 + } 183 + 184 + /* 185 + * We don't own the region. We must not free it. 186 + * 187 + * Setting this bit for a boot services region really 188 + * doesn't make sense as far as the firmware is 189 + * concerned, but it does provide us with a way to tag 190 + * those regions that must not be paired with 191 + * free_bootmem_late(). 192 + */ 193 + md->attribute |= EFI_MEMORY_RUNTIME; 191 194 } 192 195 } 193 196 ··· 228 183 md->type != EFI_BOOT_SERVICES_DATA) 229 184 continue; 230 185 231 - /* Could not reserve boot area */ 232 - if (!size) 186 + /* Do not free, someone else owns it: */ 187 + if (md->attribute & EFI_MEMORY_RUNTIME) 233 188 continue; 234 189 235 190 free_bootmem_late(start, size);