Source-Changes-HG archive
[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index][Old Index]
[src/trunk]: src/sys/arch/aarch64/aarch64 Use the PAR register to check for a...
details: https://anonhg.NetBSD.org/src/rev/02aa5f59e739
branches: trunk
changeset: 366523:02aa5f59e739
user: ryo <ryo%NetBSD.org@localhost>
date: Sun May 29 16:39:22 2022 +0000
description:
Use the PAR register to check for accessibility in db_(read|write)_bytes().
db_(read|write)_bytes() uses the TTBR[01] at that time, so it must check
if it is accessible in context at that time, not pmap_extract()
which uses the struct pmap of the process.
- It also checks if the address is writable.
- db_write_bytes() also requires ARMV81_PAN control.
diffstat:
sys/arch/aarch64/aarch64/db_interface.c | 58 ++++++++++++++++++++++++--------
1 files changed, 43 insertions(+), 15 deletions(-)
diffs (120 lines):
diff -r 6bd4d2491b9c -r 02aa5f59e739 sys/arch/aarch64/aarch64/db_interface.c
--- a/sys/arch/aarch64/aarch64/db_interface.c Sun May 29 16:30:44 2022 +0000
+++ b/sys/arch/aarch64/aarch64/db_interface.c Sun May 29 16:39:22 2022 +0000
@@ -1,4 +1,4 @@
-/* $NetBSD: db_interface.c,v 1.17 2022/05/26 17:11:05 ryo Exp $ */
+/* $NetBSD: db_interface.c,v 1.18 2022/05/29 16:39:22 ryo Exp $ */
/*
* Copyright (c) 2017 Ryo Shimizu <ryo%nerv.org@localhost>
@@ -27,7 +27,7 @@
*/
#include <sys/cdefs.h>
-__KERNEL_RCSID(0, "$NetBSD: db_interface.c,v 1.17 2022/05/26 17:11:05 ryo Exp $");
+__KERNEL_RCSID(0, "$NetBSD: db_interface.c,v 1.18 2022/05/29 16:39:22 ryo Exp $");
#include <sys/param.h>
#include <sys/types.h>
@@ -39,7 +39,9 @@
#include <uvm/pmap/pmap_pvt.h>
#endif
+#include <aarch64/armreg.h>
#include <aarch64/db_machdep.h>
+#include <aarch64/locore.h>
#include <aarch64/machdep.h>
#include <aarch64/pmap.h>
@@ -57,19 +59,40 @@
db_regs_t ddb_regs;
-static int
-db_validate_address(vaddr_t addr)
+static bool
+db_accessible_address(vaddr_t addr, bool readonly)
{
- struct proc *p = curcpu()->ci_onproc->l_proc;
- struct pmap *pmap;
+ register_t s;
+ uint64_t par;
+ int space;
+
+ space = aarch64_addressspace(addr);
+ if (space != AARCH64_ADDRSPACE_LOWER &&
+ space != AARCH64_ADDRSPACE_UPPER)
+ return false;
+
+ s = daif_disable(DAIF_I|DAIF_F);
- if (!p || !p->p_vmspace || !p->p_vmspace->vm_map.pmap ||
- addr >= VM_MAXUSER_ADDRESS)
- pmap = pmap_kernel();
- else
- pmap = p->p_vmspace->vm_map.pmap;
+ switch (aarch64_addressspace(addr)) {
+ case AARCH64_ADDRSPACE_LOWER:
+ if (readonly)
+ reg_s1e0r_write(addr);
+ else
+ reg_s1e0w_write(addr);
+ break;
+ case AARCH64_ADDRSPACE_UPPER:
+ if (readonly)
+ reg_s1e1r_write(addr);
+ else
+ reg_s1e1w_write(addr);
+ break;
+ }
+ isb();
+ par = reg_par_el1_read();
- return (pmap_extract(pmap, addr, NULL) == false);
+ reg_daif_write(s);
+
+ return ((par & PAR_F) == 0);
}
void
@@ -82,7 +105,7 @@
const vaddr_t va = (vaddr_t)src;
uintptr_t tmp;
- if (lastpage != atop(va) && db_validate_address(va)) {
+ if (lastpage != atop(va) && !db_accessible_address(va, true)) {
db_printf("address %p is invalid\n", src);
memset(data, 0, size); /* stubs are filled by zero */
return;
@@ -190,17 +213,19 @@
data += s;
}
- /* XXX: need to check read only block/page */
for (dst = (char *)addr; size > 0;) {
const vaddr_t va = (vaddr_t)dst;
uintptr_t tmp;
- if (lastpage != atop(va) && db_validate_address(va)) {
+ if (lastpage != atop(va) && !db_accessible_address(va, false)) {
db_printf("address %p is invalid\n", dst);
return;
}
lastpage = atop(va);
+ if (aarch64_pan_enabled)
+ reg_pan_write(0); /* disable PAN */
+
tmp = (uintptr_t)dst | (uintptr_t)data;
if (size >= 8 && (tmp & 7) == 0) {
*(uint64_t *)dst = *(const uint64_t *)data;
@@ -221,6 +246,9 @@
*dst++ = *data++;
size--;
}
+
+ if (aarch64_pan_enabled)
+ reg_pan_write(1); /* enable PAN */
}
}
Home |
Main Index |
Thread Index |
Old Index