summaryrefslogtreecommitdiff
path: root/sys/arch/amd64
diff options
context:
space:
mode:
authorPhilip Guenther <guenther@cvs.openbsd.org>2022-11-07 01:41:58 +0000
committerPhilip Guenther <guenther@cvs.openbsd.org>2022-11-07 01:41:58 +0000
commit079941ccc68343241f45e4a554061c5b2b6c689f (patch)
tree85e6631aa7754d69fc2ac16c212913ca961c089b /sys/arch/amd64
parent2f479c799896ce4d1e1e0332be560926bb839429 (diff)
In kpageflttrap(), validate a non-NULL pcb_onfault against an array
of permitted addresses, done via .nofault* sections that end up in the linked kernel's rodata. ok deraadt@ kettenis@
Diffstat (limited to 'sys/arch/amd64')
-rw-r--r--sys/arch/amd64/amd64/copy.S9
-rw-r--r--sys/arch/amd64/amd64/efi_machdep.c3
-rw-r--r--sys/arch/amd64/amd64/trap.c15
-rw-r--r--sys/arch/amd64/conf/ld.script6
4 files changed, 29 insertions, 4 deletions
diff --git a/sys/arch/amd64/amd64/copy.S b/sys/arch/amd64/amd64/copy.S
index 73dcefa058f..87bdd002952 100644
--- a/sys/arch/amd64/amd64/copy.S
+++ b/sys/arch/amd64/amd64/copy.S
@@ -1,4 +1,4 @@
-/* $OpenBSD: copy.S,v 1.14 2021/09/04 22:15:33 bluhm Exp $ */
+/* $OpenBSD: copy.S,v 1.15 2022/11/07 01:41:57 guenther Exp $ */
/* $NetBSD: copy.S,v 1.1 2003/04/26 18:39:26 fvdl Exp $ */
/*
@@ -44,6 +44,11 @@
#include <machine/asm.h>
#include <machine/codepatch.h>
+#define DECLARE_ONFAULT(x) \
+ .pushsection .nofault.0, "a" ;\
+ .quad x ;\
+ .popsection
+
/*
* Copy routines from and to userland, plus a few more. See the
* section 9 manpages for info. Some cases can be optimized more.
@@ -183,6 +188,7 @@ ENTRY(copyin)
lfence
NENTRY(copy_fault)
+DECLARE_ONFAULT(copy_fault)
SMAP_CLAC
movq CPUVAR(CURPCB),%rdx
popq PCB_ONFAULT(%rdx)
@@ -277,6 +283,7 @@ ENTRY(copyinstr)
jmp copystr_return
ENTRY(copystr_fault)
+DECLARE_ONFAULT(copystr_fault)
movl $EFAULT,%eax
copystr_return:
SMAP_CLAC
diff --git a/sys/arch/amd64/amd64/efi_machdep.c b/sys/arch/amd64/amd64/efi_machdep.c
index 90716cb32e8..40ed5004b6c 100644
--- a/sys/arch/amd64/amd64/efi_machdep.c
+++ b/sys/arch/amd64/amd64/efi_machdep.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: efi_machdep.c,v 1.3 2022/11/04 16:49:31 kettenis Exp $ */
+/* $OpenBSD: efi_machdep.c,v 1.4 2022/11/07 01:41:57 guenther Exp $ */
/*
* Copyright (c) 2022 Mark Kettenis <kettenis@openbsd.org>
@@ -236,6 +236,7 @@ efi_fault(void)
{
longjmp(&efi_jmpbuf);
}
+__asm(".pushsection .nofault, \"a\"; .quad efi_fault; .popsection");
void
efi_enter(struct efi_softc *sc)
diff --git a/sys/arch/amd64/amd64/trap.c b/sys/arch/amd64/amd64/trap.c
index ffda7e2609b..61f150321da 100644
--- a/sys/arch/amd64/amd64/trap.c
+++ b/sys/arch/amd64/amd64/trap.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: trap.c,v 1.92 2022/11/04 16:49:31 kettenis Exp $ */
+/* $OpenBSD: trap.c,v 1.93 2022/11/07 01:41:57 guenther Exp $ */
/* $NetBSD: trap.c,v 1.2 2003/05/04 23:51:56 fvdl Exp $ */
/*-
@@ -226,6 +226,19 @@ kpageflttrap(struct trapframe *frame, uint64_t cr2)
return 0;
pcb = &p->p_addr->u_pcb;
+ if (pcb->pcb_onfault != NULL) {
+ extern caddr_t __nofault_start[], __nofault_end[];
+ caddr_t *nf = __nofault_start;
+ while (*nf++ != pcb->pcb_onfault) {
+ if (nf >= __nofault_end) {
+ KERNEL_LOCK();
+ fault("invalid pcb_nofault=%lx",
+ (long)pcb->pcb_onfault);
+ return 0;
+ /* retain kernel lock */
+ }
+ }
+ }
/* This will only trigger if SMEP is enabled */
if (pcb->pcb_onfault == NULL && cr2 <= VM_MAXUSER_ADDRESS &&
diff --git a/sys/arch/amd64/conf/ld.script b/sys/arch/amd64/conf/ld.script
index 18298f8b8c3..c02f60c66cb 100644
--- a/sys/arch/amd64/conf/ld.script
+++ b/sys/arch/amd64/conf/ld.script
@@ -1,4 +1,4 @@
-/* $OpenBSD: ld.script,v 1.18 2022/09/02 09:02:37 mlarkin Exp $ */
+/* $OpenBSD: ld.script,v 1.19 2022/11/07 01:41:57 guenther Exp $ */
/*
* Copyright (c) 2009 Tobias Weingartner <weingart@tepid.org>
@@ -85,6 +85,10 @@ SECTIONS
{
__rodata_start = ABSOLUTE(.);
*(.rodata .rodata.*)
+ . = ALIGN(8);
+ __nofault_start = ABSOLUTE(.);
+ *(.nofault.*) *(.nofault)
+ __nofault_end = ABSOLUTE(.);
*(.codepatch)
*(.codepatchend)
} :rodata =0xcccccccc