Turn off IBRS on suspend.

Resume starts CPU from the init state, which clears any loaded
microcode updates.  As result, IBRS MSRs are no longer available,
until the microcode is reloaded.

I have to forcibly clear cpu_stdext_feature3, which assumes that CPUID
leaf 7 reg %ebx does not report anything except Meltdown/Spectre bugs
bits.  If future CPUs add new bits there, hw_ibrs_recalculate() and
identify_cpu1()/identify_cpu2() need to be adjusted for that.

Submitted and tested by:	Michael Danilov <mike.d.ft402@gmail.com>
PR:	227866
Sponsored by:	The FreeBSD Foundation
MFC after:	1 week
Differential revision:	https://reviews.freebsd.org/D15236
This commit is contained in:
Konstantin Belousov 2018-04-30 20:18:32 +00:00
parent 47280ef170
commit 986c4ca387
2 changed files with 14 additions and 1 deletions

View File

@ -209,6 +209,10 @@ acpi_sleep_machdep(struct acpi_softc *sc, int state)
{
ACPI_STATUS status;
struct pcb *pcb;
#ifdef __amd64__
struct pcpu *pc;
int i;
#endif
if (sc->acpi_wakeaddr == 0ul)
return (-1); /* couldn't alloc wake memory */
@ -238,6 +242,14 @@ acpi_sleep_machdep(struct acpi_softc *sc, int state)
return (0); /* couldn't sleep */
}
#endif
#ifdef __amd64__
hw_ibrs_active = 0;
cpu_stdext_feature3 = 0;
CPU_FOREACH(i) {
pc = pcpu_find(i);
pc->pc_ibpb_set = 0;
}
#endif
WAKECODE_FIXUP(resume_beep, uint8_t, (acpi_resume_beep != 0));
WAKECODE_FIXUP(reset_video, uint8_t, (acpi_reset_video != 0));

View File

@ -83,7 +83,8 @@ extern int _ugssel;
extern int use_xsave;
extern uint64_t xsave_mask;
extern u_int max_apic_id;
extern int pti;
extern int pti;
extern int hw_ibrs_active;
struct pcb;
struct thread;