-/* $OpenBSD: locore.S,v 1.91 2017/10/10 07:04:05 mlarkin Exp $ */
+/* $OpenBSD: locore.S,v 1.92 2018/01/06 22:03:12 guenther Exp $ */
/* $NetBSD: locore.S,v 1.13 2004/03/25 18:33:17 drochner Exp $ */
/*
btrl $CPUF_USERSEGS_BIT, CPUVAR(FLAGS)
jnc restore_saved
- /* set %ds, %es, and %fs to expected value to prevent info leak */
+ /* set %ds, %es, %fs, and %gs to expected value to prevent info leak */
movw $(GSEL(GUDATA_SEL, SEL_UPL)),%ax
movw %ax,%ds
movw %ax,%es
movw %ax,%fs
+ cli /* block interrupts when on user GS.base */
+ swapgs /* switch from kernel to user GS.base */
+ movw %ax,%gs /* set %gs to UDATA and GS.base to 0 */
+ swapgs /* back to kernel GS.base */
restore_saved:
/*
-/* $OpenBSD: machdep.c,v 1.236 2017/12/11 05:27:40 deraadt Exp $ */
+/* $OpenBSD: machdep.c,v 1.237 2018/01/06 22:03:12 guenther Exp $ */
/* $NetBSD: machdep.c,v 1.3 2003/05/07 22:58:18 fvdl Exp $ */
/*-
/*
* Force the userspace FS.base to be reloaded from the PCB on return from
- * the kernel, and reset most the segment registers (%ds, %es, and %fs)
+ * the kernel, and reset the segment registers (%ds, %es, %fs, and %gs)
* to their expected userspace value.
*/
void
reset_segs(void)
{
/*
- * Segment registers (%ds, %es, %fs, %gs) aren't in the trapframe.
- * %gs is reset on return to userspace to avoid having to deal with
- * swapgs; others are reset on context switch and here. This
- * operates like the cpu_switchto() sequence: if we haven't reset
- * %[def]s already, do so now.
- */
+ * This operates like the cpu_switchto() sequence: if we
+ * haven't reset %[defg]s already, do so now.
+ */
if (curcpu()->ci_flags & CPUF_USERSEGS) {
curcpu()->ci_flags &= ~CPUF_USERSEGS;
__asm volatile(
"movw %%ax,%%ds\n\t"
"movw %%ax,%%es\n\t"
- "movw %%ax,%%fs" : : "a"(GSEL(GUDATA_SEL, SEL_UPL)));
+ "movw %%ax,%%fs\n\t"
+ "cli\n\t" /* block intr when on user GS.base */
+ "swapgs\n\t" /* swap from kernel to user GS.base */
+ "movw %%ax,%%gs\n\t"/* set %gs to UDATA and GS.base to 0 */
+ "swapgs\n\t" /* back to kernel GS.base */
+ "sti" : : "a"(GSEL(GUDATA_SEL, SEL_UPL)));
}
}
-/* $OpenBSD: frameasm.h,v 1.10 2016/09/04 09:22:28 mpi Exp $ */
+/* $OpenBSD: frameasm.h,v 1.11 2018/01/06 22:03:12 guenther Exp $ */
/* $NetBSD: frameasm.h,v 1.1 2003/04/26 18:39:40 fvdl Exp $ */
#ifndef _AMD64_MACHINE_FRAMEASM_H
shrq $32,%rdx ; \
movl $MSR_FSBASE,%ecx ; \
wrmsr ; \
-99: movw $(GSEL(GUDATA_SEL, SEL_UPL)),%ax ; \
- cli ; \
- swapgs ; \
- movw %ax,%gs
+99: cli ; \
+ swapgs
#define INTR_FAKE_TRAP 0xbadabada