diff options
author | Mark Kettenis <kettenis@cvs.openbsd.org> | 2018-08-15 20:18:32 +0000 |
---|---|---|
committer | Mark Kettenis <kettenis@cvs.openbsd.org> | 2018-08-15 20:18:32 +0000 |
commit | d9871b145155a6c13358f6679537449ae6db7da2 (patch) | |
tree | 8c55cc838325ae9cb8e4fadbe6784b35293819a5 /sys/arch/arm64 | |
parent | d06702b247672e695e060713be9a1a14ef28194d (diff) |
Use atomic instructions to keep track of what ASIDs are in use. This makes
pmap_free_asid() and therefore pmap_destroy() mpsafe which is important since
we might end up calling that function without holding the kernel lock
as a result of releasing a reference in pmap_page_protect(9).
ok visa@
Diffstat (limited to 'sys/arch/arm64')
-rw-r--r-- | sys/arch/arm64/arm64/pmap.c | 14 |
1 files changed, 7 insertions, 7 deletions
diff --git a/sys/arch/arm64/arm64/pmap.c b/sys/arch/arm64/arm64/pmap.c index 4641e0f0305..af2294bead1 100644 --- a/sys/arch/arm64/arm64/pmap.c +++ b/sys/arch/arm64/arm64/pmap.c @@ -1,4 +1,4 @@ -/* $OpenBSD: pmap.c,v 1.54 2018/06/01 23:10:59 kettenis Exp $ */ +/* $OpenBSD: pmap.c,v 1.55 2018/08/15 20:18:31 kettenis Exp $ */ /* * Copyright (c) 2008-2009,2014-2016 Dale Rahn <drahn@dalerahn.com> * @@ -2169,7 +2169,7 @@ pmap_map_early(paddr_t spa, psize_t len) */ #define NUM_ASID (1 << 16) -uint64_t pmap_asid[NUM_ASID / 64]; +uint32_t pmap_asid[NUM_ASID / 32]; void pmap_allocate_asid(pmap_t pm) @@ -2178,10 +2178,10 @@ pmap_allocate_asid(pmap_t pm) do { asid = arc4random() & (NUM_ASID - 2); - bit = (asid & (64 - 1)); - } while (asid == 0 || (pmap_asid[asid / 64] & (3ULL << bit))); + bit = (asid & (32 - 1)); + } while (asid == 0 || (pmap_asid[asid / 32] & (3U << bit))); - pmap_asid[asid / 64] |= (3ULL << bit); + atomic_setbits_int(&pmap_asid[asid / 32], 3U << bit); pm->pm_asid = asid; } @@ -2194,8 +2194,8 @@ pmap_free_asid(pmap_t pm) cpu_tlb_flush_asid_all((uint64_t)pm->pm_asid << 48); cpu_tlb_flush_asid_all((uint64_t)(pm->pm_asid | ASID_USER) << 48); - bit = (pm->pm_asid & (64 - 1)); - pmap_asid[pm->pm_asid / 64] &= ~(3ULL << bit); + bit = (pm->pm_asid & (32 - 1)); + atomic_clearbits_int(&pmap_asid[pm->pm_asid / 32], 3U << bit); } void |