svn commit: r51482 - in head/share: security/advisories security/patches/SA-18:03 xml

Gordon Tetlow <[email protected]>
Newsgroups gmane.os.freebsd.devel.cvs.doc
Message-ID <[email protected]>
Author: gordon (src,ports committer)
Date: Wed Mar 14 04:14:13 2018
New Revision: 51482
URL: https://svnweb.freebsd.org/changeset/doc/51482

Log:
  Add FreeBSD-SA-18:03.speculative_execution.
  
  Approved by:	so

Added:
  head/share/security/advisories/FreeBSD-SA-18:03.speculative_execution.asc   (contents, props changed)
  head/share/security/patches/SA-18:03/
  head/share/security/patches/SA-18:03/speculative_execution-amd64-11.patch   (contents, props changed)
  head/share/security/patches/SA-18:03/speculative_execution-amd64-11.patch.asc   (contents, props changed)
Modified:
  head/share/xml/advisories.xml

Added: head/share/security/advisories/FreeBSD-SA-18:03.speculative_execution.asc
==============================================================================
--- /dev/null	00:00:00 1970	(empty, because file is newly added)
+++ head/share/security/advisories/FreeBSD-SA-18:03.speculative_execution.asc	Wed Mar 14 04:14:13 2018	(r51482)
@@ -0,0 +1,206 @@
+-----BEGIN PGP SIGNED MESSAGE-----
+Hash: SHA512
+
+=============================================================================
+FreeBSD-SA-18:03.speculative_execution                      Security Advisory
+                                                          The FreeBSD Project
+
+Topic:          Speculative Execution Vulnerabilities
+
+Category:       core
+Module:         kernel
+Announced:      2018-03-14
+Credits:        Jann Horn (Google Project Zero); Werner Haas, Thomas
+                Prescher (Cyberus Technology); Daniel Gruss, Moritz Lipp,
+                Stefan Mangard, Michael Schwarz (Graz University of
+                Technology); Paul Kocher; Daniel Genkin (University of
+                Pennsylvania and University of Maryland), Mike Hamburg
+                (Rambus); Yuval Yarom (University of Adelaide and Data6)
+Affects:        All supported versions of FreeBSD.
+Corrected:      2018-02-17 18:00:01 UTC (stable/11, 11.1-STABLE)
+                2018-03-14 04:00:00 UTC (releng/11.1, 11.1-RELEASE-p8)
+CVE Name:       CVE-2017-5715, CVE-2017-5754
+
+Special Note:	Speculative execution vulnerability mitigation is a work
+                in progress.  This advisory addresses the most significant
+                issues for FreeBSD 11.1 on amd64 CPUs.  We expect to update
+                this advisory to include 10.x for amd64 CPUs.  Future FreeBSD
+                releases will address this issue on i386 and other CPUs.
+                freebsd-update will include changes on i386 as part of this
+                update due to common code changes shared between amd64 and
+                i386, however it contains no functional changes for i386 (in
+                particular, it does not mitigate the issue on i386).
+
+For general information regarding FreeBSD Security Advisories,
+including descriptions of the fields above, security branches, and the
+following sections, please visit <URL:https://security.FreeBSD.org/>.
+
+I.   Background
+
+Many modern processors have implementation issues that allow unprivileged
+attackers to bypass user-kernel or inter-process memory access restrictions
+by exploiting speculative execution and shared resources (for example,
+caches).
+
+II.  Problem Description
+
+A number of issues relating to speculative execution were found last year
+and publicly announced January 3rd.  Two of these, known as Meltdown and
+Spectre V2, are addressed here.
+
+CVE-2017-5754 (Meltdown)
+- ------------------------
+
+This issue relies on an affected CPU speculatively executing instructions
+beyond a faulting instruction.  When this happens, changes to architectural
+state are not committed, but observable changes may be left in micro-
+architectural state (for example, cache).  This may be used to infer
+privileged data.
+
+CVE-2017-5715 (Spectre V2)
+- --------------------------
+
+Spectre V2 uses branch target injection to speculatively execute kernel code
+at an address under the control of an attacker.
+
+III.  Impact
+
+An attacker may be able to read secret data from the kernel or from a
+process when executing untrusted code (for example, in a web browser).
+
+IV.  Workaround
+
+No workaround is available.
+
+V.   Solution
+
+Perform one of the following:
+
+1) Upgrade your vulnerable system to a supported FreeBSD stable or
+release / security branch (releng) dated after the correction date,
+and reboot.
+
+2) To update your vulnerable system via a binary patch:
+
+Systems running a RELEASE version of FreeBSD on the i386 or amd64
+platforms can be updated via the freebsd-update(8) utility, followed
+by a reboot into the new kernel:
+
+# freebsd-update fetch
+# freebsd-update install
+# shutdown -r now
+
+3) To update your vulnerable system via a source code patch:
+
+The following patches have been verified to apply to the applicable
+FreeBSD release branches.
+
+a) Download the relevant patch from the location below, and verify the
+detached PGP signature using your PGP utility.
+
+[FreeBSD 11.1]
+# fetch https://security.FreeBSD.org/patches/SA-18:03/speculative_execution-amd64-11.patch
+# fetch https://security.FreeBSD.org/patches/SA-18:03/speculative_execution-amd64-11.patch.asc
+# gpg --verify speculative_execution-amd64-11.patch.asc
+
+b) Apply the patch.  Execute the following commands as root:
+
+# cd /usr/src
+# patch < /path/to/patch
+
+c) Recompile your kernel as described in
+<URL:https://www.FreeBSD.org/handbook/kernelconfig.html> and reboot the
+system.
+
+VI.  Correction details
+
+CVE-2017-5754 (Meltdown)
+- ------------------------
+
+The mitigation is known as Page Table Isolation (PTI).  PTI largely separates
+kernel and user mode page tables, so that even during speculative execution
+most of the kernel's data is unmapped and not accessible.
+
+A demonstration of the Meltdown vulnerability is available at
+https://github.com/dag-erling/meltdown.  A positive result is definitive
+(that is, the vulnerability exists with certainty).  A negative result
+indicates either that the CPU is not affected, or that the test is not
+capable of demonstrating the issue on the CPU (and may need to be modified).
+
+A patched kernel will automatically enable PTI on Intel CPUs.  The status can
+be checked via the vm.pmap.pti sysctl:
+
+# sysctl vm.pmap.pti
+vm.pmap.pti: 1
+
+The default setting can be overridden by setting the loader tunable
+vm.pmap.pti to 1 or 0 in /boot/loader.conf.  This setting takes effect only
+at boot.
+
+PTI introduces a performance regression.  The observed performance loss is
+significant in microbenchmarks of system call overhead, but is much smaller
+for many real workloads.
+
+CVE-2017-5715 (Spectre V2)
+- --------------------------
+
+There are two common mitigations for Spectre V2.  This patch includes a
+mitigation using Indirect Branch Restricted Speculation, a feature available
+via a microcode update from processor manufacturers.  The alternate
+mitigation, Retpoline, is a feature available in newer compilers.  The
+feasibility of applying Retpoline to stable branches and/or releases is under
+investigation.
+
+The patch includes the IBRS mitigation for Spectre V2.  To use the mitigation
+the system must have an updated microcode; with older microcode a patched
+kernel will function without the mitigation.
+
+IBRS can be disabled via the hw.ibrs_disable sysctl (and tunable), and the
+status can be checked via the hw.ibrs_active sysctl.  IBRS may be enabled or
+disabled at runtime.  Additional detail on microcode updates will follow.
+
+The following list contains the correction revision numbers for each
+affected branch.
+
+Branch/path                                                      Revision
+- -------------------------------------------------------------------------
+stable/11/                                                        r329462
+releng/11.1/                                                      r330908
+- -------------------------------------------------------------------------
+
+To see which files were modified by a particular revision, run the
+following command, replacing NNNNNN with the revision number, on a
+machine with Subversion installed:
+
+# svn diff -cNNNNNN --summarize svn://svn.freebsd.org/base
+
+Or visit the following URL, replacing NNNNNN with the revision number:
+
+<URL:https://svnweb.freebsd.org/base?view=revision&revision=NNNNNN>
+
+VII.  References
+
+<URL:https://cve.mitre.org/cgi-bin/cvename.cgi?name=CVE-2017-5715>
+
+<URL:https://cve.mitre.org/cgi-bin/cvename.cgi?name=CVE-2017-5754>
+
+The latest revision of this advisory is available at
+<URL:https://security.FreeBSD.org/advisories/FreeBSD-SA-18:03.speculative_execution.asc>
+-----BEGIN PGP SIGNATURE-----
+
+iQKTBAEBCgB9FiEE/A6HiuWv54gCjWNV05eS9J6n5cIFAlqon0RfFIAAAAAALgAo
+aXNzdWVyLWZwckBub3RhdGlvbnMub3BlbnBncC5maWZ0aGhvcnNlbWFuLm5ldEZD
+MEU4NzhBRTVBRkU3ODgwMjhENjM1NUQzOTc5MkY0OUVBN0U1QzIACgkQ05eS9J6n
+5cKORw/+Lc5lxLhDgU1rQ0JF6sb2b80Ly5k+rJLXFWBvmEQt0uVyVkF4TMJ99M04
+bcmrLbT4Pl0Csh/iEYvZQ4el12KvPDApHszsLTBgChD+KfCLvCZvBZzasgDWGD0E
+JhL4eIX0wjJ4oGGsT+TAqkmwXyAMJgWW/ZgZPFVXocylZTL3fV4g52VdG1Jnd2yu
+hnkViH2kVlVJqXX9AHlenIUfEmUiRUGrMh5oPPpFYDDmfJ+enZ8QLxfZtOKIliD7
+u+2GP8V/bvaErkxqF5wwobybrBOMXpq9Y/fWw0EH/om7myevj/oORqK+ZmGZ17bl
+IRbdWxgjc1hN2TIMVn9q9xX6i0I0wSPwbpLYagKnSnE8WNVUTZUteaj1GKGTG1rj
+DFH2zOLlbRr/IXUFldM9b6VbZX6G5Ijxwy1DJzB/0KL5ZTbAReUR0pqHR7xpulbJ
+eDv8SKCwYiUpMuwPOXNdVlVLZSsH5/9A0cyjH3+E+eIhM8qyxw7iRFwA0DxnGVkr
+tkMo51Vl3Gl7JFFimGKljsE9mBh00m8B0WYJwknvfhdehO4WripcwI7/V5zL6cwj
+s018kaW4Xm77LOz6P1iN8nbcjZ9gN2AsPYUYYZqJxjCcZ7r489Hg9BhbDf0QtC0R
+gnwZWiZ/KuAy0C6vaHljsm0xPEM5nBz/yScFXDbuhEdmEgBBD6w=
+=fqrI
+-----END PGP SIGNATURE-----

Added: head/share/security/patches/SA-18:03/speculative_execution-amd64-11.patch
==============================================================================
--- /dev/null	00:00:00 1970	(empty, because file is newly added)
+++ head/share/security/patches/SA-18:03/speculative_execution-amd64-11.patch	Wed Mar 14 04:14:13 2018	(r51482)
@@ -0,0 +1,4618 @@
+--- sys/amd64/amd64/apic_vector.S.orig
++++ sys/amd64/amd64/apic_vector.S
+@@ -2,7 +2,13 @@
+  * Copyright (c) 1989, 1990 William F. Jolitz.
+  * Copyright (c) 1990 The Regents of the University of California.
+  * All rights reserved.
++ * Copyright (c) 2014-2018 The FreeBSD Foundation
++ * All rights reserved.
+  *
++ * Portions of this software were developed by
++ * Konstantin Belousov <[email protected]> under sponsorship from
++ * the FreeBSD Foundation.
++ *
+  * Redistribution and use in source and binary forms, with or without
+  * modification, are permitted provided that the following conditions
+  * are met:
+@@ -38,12 +44,12 @@
+ 
+ #include "opt_smp.h"
+ 
++#include "assym.s"
++
+ #include <machine/asmacros.h>
+ #include <machine/specialreg.h>
+ #include <x86/apicreg.h>
+ 
+-#include "assym.s"
+-
+ #ifdef SMP
+ #define LK	lock ;
+ #else
+@@ -73,30 +79,28 @@
+  * translates that into a vector, and passes the vector to the
+  * lapic_handle_intr() function.
+  */
+-#define	ISR_VEC(index, vec_name)					\
+-	.text ;								\
+-	SUPERALIGN_TEXT ;						\
+-IDTVEC(vec_name) ;							\
+-	PUSH_FRAME ;							\
+-	FAKE_MCOUNT(TF_RIP(%rsp)) ;					\
+-	cmpl	$0,x2apic_mode ;					\
+-	je	1f ;							\
+-	movl	$(MSR_APIC_ISR0 + index),%ecx ;				\
+-	rdmsr ;								\
+-	jmp	2f ;							\
+-1: ;									\
+-	movq	lapic_map, %rdx ;	/* pointer to local APIC */	\
+-	movl	LA_ISR + 16 * (index)(%rdx), %eax ;	/* load ISR */	\
+-2: ;									\
+-	bsrl	%eax, %eax ;	/* index of highest set bit in ISR */	\
+-	jz	3f ;							\
+-	addl	$(32 * index),%eax ;					\
+-	movq	%rsp, %rsi	;                                       \
+-	movl	%eax, %edi ;	/* pass the IRQ */			\
+-	call	lapic_handle_intr ;					\
+-3: ;									\
+-	MEXITCOUNT ;							\
++	.macro	ISR_VEC	index, vec_name
++	INTR_HANDLER	\vec_name
++	FAKE_MCOUNT(TF_RIP(%rsp))
++	cmpl	$0,x2apic_mode
++	je	1f
++	movl	$(MSR_APIC_ISR0 + \index),%ecx
++	rdmsr
++	jmp	2f
++1:
++	movq	lapic_map, %rdx		/* pointer to local APIC */
++	movl	LA_ISR + 16 * (\index)(%rdx), %eax	/* load ISR */
++2:
++	bsrl	%eax, %eax	/* index of highest set bit in ISR */
++	jz	3f
++	addl	$(32 * \index),%eax
++	movq	%rsp, %rsi
++	movl	%eax, %edi	/* pass the IRQ */
++	call	lapic_handle_intr
++3:
++	MEXITCOUNT
+ 	jmp	doreti
++	.endm
+ 
+ /*
+  * Handle "spurious INTerrupts".
+@@ -108,26 +112,21 @@
+ 	.text
+ 	SUPERALIGN_TEXT
+ IDTVEC(spuriousint)
+-
+ 	/* No EOI cycle used here */
+-
+ 	jmp	doreti_iret
+ 
+-	ISR_VEC(1, apic_isr1)
+-	ISR_VEC(2, apic_isr2)
+-	ISR_VEC(3, apic_isr3)
+-	ISR_VEC(4, apic_isr4)
+-	ISR_VEC(5, apic_isr5)
+-	ISR_VEC(6, apic_isr6)
+-	ISR_VEC(7, apic_isr7)
++	ISR_VEC	1, apic_isr1
++	ISR_VEC	2, apic_isr2
++	ISR_VEC	3, apic_isr3
++	ISR_VEC	4, apic_isr4
++	ISR_VEC	5, apic_isr5
++	ISR_VEC	6, apic_isr6
++	ISR_VEC	7, apic_isr7
+ 
+ /*
+  * Local APIC periodic timer handler.
+  */
+-	.text
+-	SUPERALIGN_TEXT
+-IDTVEC(timerint)
+-	PUSH_FRAME
++	INTR_HANDLER	timerint
+ 	FAKE_MCOUNT(TF_RIP(%rsp))
+ 	movq	%rsp, %rdi
+ 	call	lapic_handle_timer
+@@ -137,10 +136,7 @@
+ /*
+  * Local APIC CMCI handler.
+  */
+-	.text
+-	SUPERALIGN_TEXT
+-IDTVEC(cmcint)
+-	PUSH_FRAME
++	INTR_HANDLER cmcint
+ 	FAKE_MCOUNT(TF_RIP(%rsp))
+ 	call	lapic_handle_cmc
+ 	MEXITCOUNT
+@@ -149,10 +145,7 @@
+ /*
+  * Local APIC error interrupt handler.
+  */
+-	.text
+-	SUPERALIGN_TEXT
+-IDTVEC(errorint)
+-	PUSH_FRAME
++	INTR_HANDLER errorint
+ 	FAKE_MCOUNT(TF_RIP(%rsp))
+ 	call	lapic_handle_error
+ 	MEXITCOUNT
+@@ -163,10 +156,7 @@
+  * Xen event channel upcall interrupt handler.
+  * Only used when the hypervisor supports direct vector callbacks.
+  */
+-	.text
+-	SUPERALIGN_TEXT
+-IDTVEC(xen_intr_upcall)
+-	PUSH_FRAME
++	INTR_HANDLER xen_intr_upcall
+ 	FAKE_MCOUNT(TF_RIP(%rsp))
+ 	movq	%rsp, %rdi
+ 	call	xen_intr_handle_upcall
+@@ -183,59 +173,59 @@
+ 	SUPERALIGN_TEXT
+ invltlb_ret:
+ 	call	as_lapic_eoi
+-	POP_FRAME
+-	jmp	doreti_iret
++	jmp	ld_regs
+ 
+ 	SUPERALIGN_TEXT
+-IDTVEC(invltlb)
+-	PUSH_FRAME
+-
++	INTR_HANDLER invltlb
+ 	call	invltlb_handler
+ 	jmp	invltlb_ret
+ 
+-IDTVEC(invltlb_pcid)
+-	PUSH_FRAME
+-
++	INTR_HANDLER invltlb_pcid
+ 	call	invltlb_pcid_handler
+ 	jmp	invltlb_ret
+ 
+-IDTVEC(invltlb_invpcid)
+-	PUSH_FRAME
+-
++	INTR_HANDLER invltlb_invpcid_nopti
+ 	call	invltlb_invpcid_handler
+ 	jmp	invltlb_ret
+ 
++	INTR_HANDLER invltlb_invpcid_pti
++	call	invltlb_invpcid_pti_handler
++	jmp	invltlb_ret
++
+ /*
+  * Single page TLB shootdown
+  */
+-	.text
++	INTR_HANDLER invlpg
++	call	invlpg_handler
++	jmp	invltlb_ret
+ 
+-	SUPERALIGN_TEXT
+-IDTVEC(invlpg)
+-	PUSH_FRAME
++	INTR_HANDLER invlpg_invpcid
++	call	invlpg_invpcid_handler
++	jmp	invltlb_ret
+ 
+-	call	invlpg_handler
++	INTR_HANDLER invlpg_pcid
++	call	invlpg_pcid_handler
+ 	jmp	invltlb_ret
+ 
+ /*
+  * Page range TLB shootdown.
+  */
+-	.text
+-	SUPERALIGN_TEXT
+-IDTVEC(invlrng)
+-	PUSH_FRAME
+-
++	INTR_HANDLER invlrng
+ 	call	invlrng_handler
+ 	jmp	invltlb_ret
+ 
++	INTR_HANDLER invlrng_invpcid
++	call	invlrng_invpcid_handler
++	jmp	invltlb_ret
++
++	INTR_HANDLER invlrng_pcid
++	call	invlrng_pcid_handler
++	jmp	invltlb_ret
++
+ /*
+  * Invalidate cache.
+  */
+-	.text
+-	SUPERALIGN_TEXT
+-IDTVEC(invlcache)
+-	PUSH_FRAME
+-
++	INTR_HANDLER invlcache
+ 	call	invlcache_handler
+ 	jmp	invltlb_ret
+ 
+@@ -242,15 +232,9 @@
+ /*
+  * Handler for IPIs sent via the per-cpu IPI bitmap.
+  */
+-	.text
+-	SUPERALIGN_TEXT
+-IDTVEC(ipi_intr_bitmap_handler)		
+-	PUSH_FRAME
+-
++	INTR_HANDLER ipi_intr_bitmap_handler
+ 	call	as_lapic_eoi
+-	
+ 	FAKE_MCOUNT(TF_RIP(%rsp))
+-
+ 	call	ipi_bitmap_handler
+ 	MEXITCOUNT
+ 	jmp	doreti
+@@ -258,13 +242,8 @@
+ /*
+  * Executed by a CPU when it receives an IPI_STOP from another CPU.
+  */
+-	.text
+-	SUPERALIGN_TEXT
+-IDTVEC(cpustop)
+-	PUSH_FRAME
+-
++	INTR_HANDLER cpustop
+ 	call	as_lapic_eoi
+-
+ 	call	cpustop_handler
+ 	jmp	doreti
+ 
+@@ -271,11 +250,7 @@
+ /*
+  * Executed by a CPU when it receives an IPI_SUSPEND from another CPU.
+  */
+-	.text
+-	SUPERALIGN_TEXT
+-IDTVEC(cpususpend)
+-	PUSH_FRAME
+-
++	INTR_HANDLER cpususpend
+ 	call	cpususpend_handler
+ 	call	as_lapic_eoi
+ 	jmp	doreti
+@@ -285,10 +260,7 @@
+  *
+  * - Calls the generic rendezvous action function.
+  */
+-	.text
+-	SUPERALIGN_TEXT
+-IDTVEC(rendezvous)
+-	PUSH_FRAME
++	INTR_HANDLER rendezvous
+ #ifdef COUNT_IPIS
+ 	movl	PCPU(CPUID), %eax
+ 	movq	ipi_rendezvous_counts(,%rax,8), %rax
+@@ -328,4 +300,8 @@
+ 	popq	%rax
+ 	jmp	doreti_iret
+ 
++	INTR_HANDLER	justreturn1
++	call	as_lapic_eoi
++	jmp	doreti
++
+ #endif /* SMP */
+--- sys/amd64/amd64/atpic_vector.S.orig
++++ sys/amd64/amd64/atpic_vector.S
+@@ -36,38 +36,35 @@
+  * master and slave interrupt controllers.
+  */
+ 
++#include "assym.s"
+ #include <machine/asmacros.h>
+ 
+-#include "assym.s"
+-
+ /*
+  * Macros for interrupt entry, call to handler, and exit.
+  */
+-#define	INTR(irq_num, vec_name) \
+-	.text ;								\
+-	SUPERALIGN_TEXT ;						\
+-IDTVEC(vec_name) ;							\
+-	PUSH_FRAME ;							\
+-	FAKE_MCOUNT(TF_RIP(%rsp)) ;					\
+-	movq	%rsp, %rsi	;                                       \
+-	movl	$irq_num, %edi; 	/* pass the IRQ */		\
+-	call	atpic_handle_intr ;					\
+-	MEXITCOUNT ;							\
++	.macro	INTR	irq_num, vec_name
++	INTR_HANDLER	\vec_name
++	FAKE_MCOUNT(TF_RIP(%rsp))
++	movq	%rsp, %rsi
++	movl	$\irq_num, %edi	 	/* pass the IRQ */
++	call	atpic_handle_intr
++	MEXITCOUNT
+ 	jmp	doreti
++	.endm
+ 
+-	INTR(0, atpic_intr0)
+-	INTR(1, atpic_intr1)
+-	INTR(2, atpic_intr2)
+-	INTR(3, atpic_intr3)
+-	INTR(4, atpic_intr4)
+-	INTR(5, atpic_intr5)
+-	INTR(6, atpic_intr6)
+-	INTR(7, atpic_intr7)
+-	INTR(8, atpic_intr8)
+-	INTR(9, atpic_intr9)
+-	INTR(10, atpic_intr10)
+-	INTR(11, atpic_intr11)
+-	INTR(12, atpic_intr12)
+-	INTR(13, atpic_intr13)
+-	INTR(14, atpic_intr14)
+-	INTR(15, atpic_intr15)
++	INTR	0, atpic_intr0
++	INTR	1, atpic_intr1
++	INTR	2, atpic_intr2
++	INTR	3, atpic_intr3
++	INTR	4, atpic_intr4
++	INTR	5, atpic_intr5
++	INTR	6, atpic_intr6
++	INTR	7, atpic_intr7
++	INTR	8, atpic_intr8
++	INTR	9, atpic_intr9
++	INTR	10, atpic_intr10
++	INTR	11, atpic_intr11
++	INTR	12, atpic_intr12
++	INTR	13, atpic_intr13
++	INTR	14, atpic_intr14
++	INTR	15, atpic_intr15
+--- sys/amd64/amd64/cpu_switch.S.orig
++++ sys/amd64/amd64/cpu_switch.S
+@@ -191,9 +191,11 @@
+ done_tss:
+ 	movq	%r8,PCPU(RSP0)
+ 	movq	%r8,PCPU(CURPCB)
+-	/* Update the TSS_RSP0 pointer for the next interrupt */
++	/* Update the COMMON_TSS_RSP0 pointer for the next interrupt */
++	cmpb	$0,pti(%rip)
++	jne	1f
+ 	movq	%r8,COMMON_TSS_RSP0(%rdx)
+-	movq	%r12,PCPU(CURTHREAD)		/* into next thread */
++1:	movq	%r12,PCPU(CURTHREAD)		/* into next thread */
+ 
+ 	/* Test if debug registers should be restored. */
+ 	testl	$PCB_DBREGS,PCB_FLAGS(%r8)
+@@ -270,7 +272,12 @@
+ 	shrq	$8,%rcx
+ 	movl	%ecx,8(%rax)
+ 	movb	$0x89,5(%rax)	/* unset busy */
+-	movl	$TSSSEL,%eax
++	cmpb	$0,pti(%rip)
++	je	1f
++	movq	PCPU(PRVSPACE),%rax
++	addq	$PC_PTI_STACK+PC_PTI_STACK_SZ*8,%rax
++	movq	%rax,COMMON_TSS_RSP0(%rdx)
++1:	movl	$TSSSEL,%eax
+ 	ltr	%ax
+ 	jmp	done_tss
+ 
+--- sys/amd64/amd64/db_trace.c.orig
++++ sys/amd64/amd64/db_trace.c
+@@ -200,6 +200,7 @@
+ 	if (name != NULL) {
+ 		if (strcmp(name, "calltrap") == 0 ||
+ 		    strcmp(name, "fork_trampoline") == 0 ||
++		    strcmp(name, "mchk_calltrap") == 0 ||
+ 		    strcmp(name, "nmi_calltrap") == 0 ||
+ 		    strcmp(name, "Xdblfault") == 0)
+ 			frame_type = TRAP;
+--- sys/amd64/amd64/exception.S.orig
++++ sys/amd64/amd64/exception.S
+@@ -1,12 +1,16 @@
+ /*-
+  * Copyright (c) 1989, 1990 William F. Jolitz.
+  * Copyright (c) 1990 The Regents of the University of California.
+- * Copyright (c) 2007 The FreeBSD Foundation
++ * Copyright (c) 2007-2018 The FreeBSD Foundation
+  * All rights reserved.
+  *
+  * Portions of this software were developed by A. Joseph Koshy under
+  * sponsorship from the FreeBSD Foundation and Google, Inc.
+  *
++ * Portions of this software were developed by
++ * Konstantin Belousov <[email protected]> under sponsorship from
++ * the FreeBSD Foundation.
++ *
+  * Redistribution and use in source and binary forms, with or without
+  * modification, are permitted provided that the following conditions
+  * are met:
+@@ -38,13 +42,13 @@
+ #include "opt_compat.h"
+ #include "opt_hwpmc_hooks.h"
+ 
++#include "assym.s"
++
+ #include <machine/asmacros.h>
+ #include <machine/psl.h>
+ #include <machine/trap.h>
+ #include <machine/specialreg.h>
+ 
+-#include "assym.s"
+-
+ #ifdef KDTRACE_HOOKS
+ 	.bss
+ 	.globl	dtrace_invop_jump_addr
+@@ -100,69 +104,62 @@
+ MCOUNT_LABEL(user)
+ MCOUNT_LABEL(btrap)
+ 
+-/* Traps that we leave interrupts disabled for.. */
+-#define	TRAP_NOEN(a)	\
+-	subq $TF_RIP,%rsp; \
+-	movl $(a),TF_TRAPNO(%rsp) ; \
+-	movq $0,TF_ADDR(%rsp) ; \
+-	movq $0,TF_ERR(%rsp) ; \
++/* Traps that we leave interrupts disabled for. */
++	.macro	TRAP_NOEN	l, trapno
++	PTI_ENTRY	\l,X\l
++	.globl	X\l
++	.type	X\l,@function
++X\l:	subq $TF_RIP,%rsp
++	movl $\trapno,TF_TRAPNO(%rsp)
++	movq $0,TF_ADDR(%rsp)
++	movq $0,TF_ERR(%rsp)
+ 	jmp alltraps_noen
+-IDTVEC(dbg)
+-	TRAP_NOEN(T_TRCTRAP)
+-IDTVEC(bpt)
+-	TRAP_NOEN(T_BPTFLT)
++	.endm
++
++	TRAP_NOEN	dbg, T_TRCTRAP
++	TRAP_NOEN	bpt, T_BPTFLT
+ #ifdef KDTRACE_HOOKS
+-IDTVEC(dtrace_ret)
+-	TRAP_NOEN(T_DTRACE_RET)
++	TRAP_NOEN	dtrace_ret, T_DTRACE_RET
+ #endif
+ 
+ /* Regular traps; The cpu does not supply tf_err for these. */
+-#define	TRAP(a)	 \
+-	subq $TF_RIP,%rsp; \
+-	movl $(a),TF_TRAPNO(%rsp) ; \
+-	movq $0,TF_ADDR(%rsp) ; \
+-	movq $0,TF_ERR(%rsp) ; \
++	.macro	TRAP	l, trapno
++	PTI_ENTRY	\l,X\l
++	.globl	X\l
++	.type	X\l,@function
++X\l:
++	subq $TF_RIP,%rsp
++	movl $\trapno,TF_TRAPNO(%rsp)
++	movq $0,TF_ADDR(%rsp)
++	movq $0,TF_ERR(%rsp)
+ 	jmp alltraps
+-IDTVEC(div)
+-	TRAP(T_DIVIDE)
+-IDTVEC(ofl)
+-	TRAP(T_OFLOW)
+-IDTVEC(bnd)
+-	TRAP(T_BOUND)
+-IDTVEC(ill)
+-	TRAP(T_PRIVINFLT)
+-IDTVEC(dna)
+-	TRAP(T_DNA)
+-IDTVEC(fpusegm)
+-	TRAP(T_FPOPFLT)
+-IDTVEC(mchk)
+-	TRAP(T_MCHK)
+-IDTVEC(rsvd)
+-	TRAP(T_RESERVED)
+-IDTVEC(fpu)
+-	TRAP(T_ARITHTRAP)
+-IDTVEC(xmm)
+-	TRAP(T_XMMFLT)
++	.endm
+ 
+-/* This group of traps have tf_err already pushed by the cpu */
+-#define	TRAP_ERR(a)	\
+-	subq $TF_ERR,%rsp; \
+-	movl $(a),TF_TRAPNO(%rsp) ; \
+-	movq $0,TF_ADDR(%rsp) ; \
++	TRAP	div, T_DIVIDE
++	TRAP	ofl, T_OFLOW
++	TRAP	bnd, T_BOUND
++	TRAP	ill, T_PRIVINFLT
++	TRAP	dna, T_DNA
++	TRAP	fpusegm, T_FPOPFLT
++	TRAP	rsvd, T_RESERVED
++	TRAP	fpu, T_ARITHTRAP
++	TRAP	xmm, T_XMMFLT
++
++/* This group of traps have tf_err already pushed by the cpu. */
++	.macro	TRAP_ERR	l, trapno
++	PTI_ENTRY	\l,X\l,has_err=1
++	.globl	X\l
++	.type	X\l,@function
++X\l:
++	subq $TF_ERR,%rsp
++	movl $\trapno,TF_TRAPNO(%rsp)
++	movq $0,TF_ADDR(%rsp)
+ 	jmp alltraps
+-IDTVEC(tss)
+-	TRAP_ERR(T_TSSFLT)
+-IDTVEC(missing)
+-	subq	$TF_ERR,%rsp
+-	movl	$T_SEGNPFLT,TF_TRAPNO(%rsp)
+-	jmp	prot_addrf
+-IDTVEC(stk)
+-	subq	$TF_ERR,%rsp
+-	movl	$T_STKFLT,TF_TRAPNO(%rsp)
+-	jmp	prot_addrf
+-IDTVEC(align)
+-	TRAP_ERR(T_ALIGNFLT)
++	.endm
+ 
++	TRAP_ERR	tss, T_TSSFLT
++	TRAP_ERR	align, T_ALIGNFLT
++
+ 	/*
+ 	 * alltraps entry point.  Use swapgs if this is the first time in the
+ 	 * kernel from userland.  Reenable interrupts if they were enabled
+@@ -174,25 +171,24 @@
+ alltraps:
+ 	movq	%rdi,TF_RDI(%rsp)
+ 	testb	$SEL_RPL_MASK,TF_CS(%rsp) /* Did we come from kernel? */
+-	jz	alltraps_testi		/* already running with kernel GS.base */
++	jz	1f		/* already running with kernel GS.base */
+ 	swapgs
+ 	movq	PCPU(CURPCB),%rdi
+ 	andl	$~PCB_FULL_IRET,PCB_FLAGS(%rdi)
+-	movw	%fs,TF_FS(%rsp)
+-	movw	%gs,TF_GS(%rsp)
+-	movw	%es,TF_ES(%rsp)
+-	movw	%ds,TF_DS(%rsp)
+-alltraps_testi:
+-	testl	$PSL_I,TF_RFLAGS(%rsp)
+-	jz	alltraps_pushregs_no_rdi
++1:	SAVE_SEGS
++	movq	%rdx,TF_RDX(%rsp)
++	movq	%rax,TF_RAX(%rsp)
++	movq	%rcx,TF_RCX(%rsp)
++	testb	$SEL_RPL_MASK,TF_CS(%rsp)
++	jz	2f
++	call	handle_ibrs_entry
++2:	testl	$PSL_I,TF_RFLAGS(%rsp)
++	jz	alltraps_pushregs_no_rax
+ 	sti
+-alltraps_pushregs_no_rdi:
++alltraps_pushregs_no_rax:
+ 	movq	%rsi,TF_RSI(%rsp)
+-	movq	%rdx,TF_RDX(%rsp)
+-	movq	%rcx,TF_RCX(%rsp)
+ 	movq	%r8,TF_R8(%rsp)
+ 	movq	%r9,TF_R9(%rsp)
+-	movq	%rax,TF_RAX(%rsp)
+ 	movq	%rbx,TF_RBX(%rsp)
+ 	movq	%rbp,TF_RBP(%rsp)
+ 	movq	%r10,TF_R10(%rsp)
+@@ -248,15 +244,18 @@
+ alltraps_noen:
+ 	movq	%rdi,TF_RDI(%rsp)
+ 	testb	$SEL_RPL_MASK,TF_CS(%rsp) /* Did we come from kernel? */
+-	jz	1f	/* already running with kernel GS.base */
++	jz	1f /* already running with kernel GS.base */
+ 	swapgs
+ 	movq	PCPU(CURPCB),%rdi
+ 	andl	$~PCB_FULL_IRET,PCB_FLAGS(%rdi)
+-1:	movw	%fs,TF_FS(%rsp)
+-	movw	%gs,TF_GS(%rsp)
+-	movw	%es,TF_ES(%rsp)
+-	movw	%ds,TF_DS(%rsp)
+-	jmp	alltraps_pushregs_no_rdi
++1:	SAVE_SEGS
++	movq	%rdx,TF_RDX(%rsp)
++	movq	%rax,TF_RAX(%rsp)
++	movq	%rcx,TF_RCX(%rsp)
++	testb	$SEL_RPL_MASK,TF_CS(%rsp)
++	jz	alltraps_pushregs_no_rax
++	call	handle_ibrs_entry
++	jmp	alltraps_pushregs_no_rax
+ 
+ IDTVEC(dblfault)
+ 	subq	$TF_ERR,%rsp
+@@ -278,10 +277,7 @@
+ 	movq	%r13,TF_R13(%rsp)
+ 	movq	%r14,TF_R14(%rsp)
+ 	movq	%r15,TF_R15(%rsp)
+-	movw	%fs,TF_FS(%rsp)
+-	movw	%gs,TF_GS(%rsp)
+-	movw	%es,TF_ES(%rsp)
+-	movw	%ds,TF_DS(%rsp)
++	SAVE_SEGS
+ 	movl	$TF_HASSEGS,TF_FLAGS(%rsp)
+ 	cld
+ 	testb	$SEL_RPL_MASK,TF_CS(%rsp) /* Did we come from kernel? */
+@@ -288,31 +284,54 @@
+ 	jz	1f			/* already running with kernel GS.base */
+ 	swapgs
+ 1:
+-	movq	%rsp,%rdi
++	movq	PCPU(KCR3),%rax
++	cmpq	$~0,%rax
++	je	2f
++	movq	%rax,%cr3
++2:	movq	%rsp,%rdi
+ 	call	dblfault_handler
+-2:
+-	hlt
+-	jmp	2b
++3:	hlt
++	jmp	3b
+ 
++	ALIGN_TEXT
++IDTVEC(page_pti)
++	testb	$SEL_RPL_MASK,PTI_CS-2*8(%rsp)
++	jz	Xpage
++	swapgs
++	pushq	%rax
++	pushq	%rdx
++	movq	%cr3,%rax
++	movq	%rax,PCPU(SAVED_UCR3)
++	PTI_UUENTRY has_err=1
++	subq	$TF_ERR,%rsp
++	movq	%rdi,TF_RDI(%rsp)
++	movq	%rax,TF_RAX(%rsp)
++	movq	%rdx,TF_RDX(%rsp)
++	movq	%rcx,TF_RCX(%rsp)
++	jmp	page_u
+ IDTVEC(page)
+ 	subq	$TF_ERR,%rsp
+-	movl	$T_PAGEFLT,TF_TRAPNO(%rsp)
+-	movq	%rdi,TF_RDI(%rsp)	/* free up a GP register */
++	movq	%rdi,TF_RDI(%rsp)	/* free up GP registers */
++	movq	%rax,TF_RAX(%rsp)
++	movq	%rdx,TF_RDX(%rsp)
++	movq	%rcx,TF_RCX(%rsp)
+ 	testb	$SEL_RPL_MASK,TF_CS(%rsp) /* Did we come from kernel? */
+-	jz	1f			/* already running with kernel GS.base */
++	jz	page_cr2		/* already running with kernel GS.base */
+ 	swapgs
+-	movq	PCPU(CURPCB),%rdi
++page_u:	movq	PCPU(CURPCB),%rdi
+ 	andl	$~PCB_FULL_IRET,PCB_FLAGS(%rdi)
+-1:	movq	%cr2,%rdi		/* preserve %cr2 before ..  */
++	movq	PCPU(SAVED_UCR3),%rax
++	movq	%rax,PCB_SAVED_UCR3(%rdi)
++	call	handle_ibrs_entry
++page_cr2:
++	movq	%cr2,%rdi		/* preserve %cr2 before ..  */
+ 	movq	%rdi,TF_ADDR(%rsp)	/* enabling interrupts. */
+-	movw	%fs,TF_FS(%rsp)
+-	movw	%gs,TF_GS(%rsp)
+-	movw	%es,TF_ES(%rsp)
+-	movw	%ds,TF_DS(%rsp)
++	SAVE_SEGS
++	movl	$T_PAGEFLT,TF_TRAPNO(%rsp)
+ 	testl	$PSL_I,TF_RFLAGS(%rsp)
+-	jz	alltraps_pushregs_no_rdi
++	jz	alltraps_pushregs_no_rax
+ 	sti
+-	jmp	alltraps_pushregs_no_rdi
++	jmp	alltraps_pushregs_no_rax
+ 
+ 	/*
+ 	 * We have to special-case this one.  If we get a trap in doreti() at
+@@ -319,30 +338,71 @@
+ 	 * the iretq stage, we'll reenter with the wrong gs state.  We'll have
+ 	 * to do a special the swapgs in this case even coming from the kernel.
+ 	 * XXX linux has a trap handler for their equivalent of load_gs().
++	 *
++	 * On the stack, we have the hardware interrupt frame to return
++	 * to usermode (faulted) and another frame with error code, for
++	 * fault.  For PTI, copy both frames to the main thread stack.
+ 	 */
+-IDTVEC(prot)
++	.macro PROTF_ENTRY name,trapno
++\name\()_pti_doreti:
++	pushq	%rax
++	pushq	%rdx
++	swapgs
++	movq	PCPU(KCR3),%rax
++	movq	%rax,%cr3
++	movq	PCPU(RSP0),%rax
++	subq	$2*PTI_SIZE-3*8,%rax /* no err, %rax, %rdx in faulted frame */
++	MOVE_STACKS	(PTI_SIZE / 4 - 3)
++	movq	%rax,%rsp
++	popq	%rdx
++	popq	%rax
++	swapgs
++	jmp	X\name
++IDTVEC(\name\()_pti)
++	cmpq	$doreti_iret,PTI_RIP-2*8(%rsp)
++	je	\name\()_pti_doreti
++	testb	$SEL_RPL_MASK,PTI_CS-2*8(%rsp) /* %rax, %rdx not yet pushed */
++	jz	X\name
++	PTI_UENTRY has_err=1
++	swapgs
++IDTVEC(\name)
+ 	subq	$TF_ERR,%rsp
+-	movl	$T_PROTFLT,TF_TRAPNO(%rsp)
++	movl	$\trapno,TF_TRAPNO(%rsp)
++	jmp	prot_addrf
++	.endm
++
++	PROTF_ENTRY	missing, T_SEGNPFLT
++	PROTF_ENTRY	stk, T_STKFLT
++	PROTF_ENTRY	prot, T_PROTFLT
++
+ prot_addrf:
+ 	movq	$0,TF_ADDR(%rsp)
+ 	movq	%rdi,TF_RDI(%rsp)	/* free up a GP register */
++	movq	%rax,TF_RAX(%rsp)
++	movq	%rdx,TF_RDX(%rsp)
++	movq	%rcx,TF_RCX(%rsp)
++	movw	%fs,TF_FS(%rsp)
++	movw	%gs,TF_GS(%rsp)
+ 	leaq	doreti_iret(%rip),%rdi
+ 	cmpq	%rdi,TF_RIP(%rsp)
+-	je	1f			/* kernel but with user gsbase!! */
++	je	5f			/* kernel but with user gsbase!! */
+ 	testb	$SEL_RPL_MASK,TF_CS(%rsp) /* Did we come from kernel? */
+-	jz	2f			/* already running with kernel GS.base */
+-1:	swapgs
+-2:	movq	PCPU(CURPCB),%rdi
++	jz	6f			/* already running with kernel GS.base */
++	swapgs
++	movq	PCPU(CURPCB),%rdi
++4:	call	handle_ibrs_entry
+ 	orl	$PCB_FULL_IRET,PCB_FLAGS(%rdi)	/* always full iret from GPF */
+-	movw	%fs,TF_FS(%rsp)
+-	movw	%gs,TF_GS(%rsp)
+ 	movw	%es,TF_ES(%rsp)
+ 	movw	%ds,TF_DS(%rsp)
+ 	testl	$PSL_I,TF_RFLAGS(%rsp)
+-	jz	alltraps_pushregs_no_rdi
++	jz	alltraps_pushregs_no_rax
+ 	sti
+-	jmp	alltraps_pushregs_no_rdi
++	jmp	alltraps_pushregs_no_rax
+ 
++5:	swapgs
++6:	movq	PCPU(CURPCB),%rdi
++	jmp	4b
++

*** DIFF OUTPUT TRUNCATED AT 1000 LINES ***
_______________________________________________
[email protected] mailing list
https://lists.freebsd.org/mailman/listinfo/svn-doc-all
To unsubscribe, send any mail to "[email protected]"
lmpx.com only provides a reader for public news (NNTP) servers. It is not affiliated with the servers or forums shown here and is not responsible for the content of articles, which is written by their respective authors.