Page MenuHomeFreeBSD

D56306.id175102.diff
No OneTemporary

D56306.id175102.diff

diff --git a/sys/arm64/arm64/mp_machdep.c b/sys/arm64/arm64/mp_machdep.c
--- a/sys/arm64/arm64/mp_machdep.c
+++ b/sys/arm64/arm64/mp_machdep.c
@@ -59,6 +59,7 @@
#include <machine/cpu_feat.h>
#include <machine/debug_monitor.h>
#include <machine/intr.h>
+#include <machine/pmap.h>
#include <machine/smp.h>
#include <machine/vmparam.h>
#ifdef VFP
@@ -579,6 +580,9 @@
return (false);
}
+ /* Allocate per-cpu data in pmap */
+ pmap_bootstrap_cpu(pcpup);
+
/* Wait for the AP to switch to its boot stack. */
while (atomic_load_int(&aps_started) < naps + 1)
cpu_spinwait();
diff --git a/sys/arm64/arm64/pmap.c b/sys/arm64/arm64/pmap.c
--- a/sys/arm64/arm64/pmap.c
+++ b/sys/arm64/arm64/pmap.c
@@ -1341,6 +1341,7 @@
void
pmap_bootstrap(void)
{
+ struct pcpu *pc;
vm_offset_t dpcpu, msgbufpv;
vm_paddr_t start_pa, pa;
size_t largest_phys_size;
@@ -1363,7 +1364,7 @@
virtual_avail = preinit_map_va + PMAP_PREINIT_MAPPING_SIZE;
virtual_avail = roundup2(virtual_avail, L1_SIZE);
- virtual_end = VM_MAX_KERNEL_ADDRESS - PMAP_MAPDEV_EARLY_SIZE;
+ virtual_end = VM_MAX_KERNEL_ADDRESS - PMAP_MAPDEV_EARLY_SIZE - L2_SIZE;
kernel_vm_end = virtual_avail;
/*
@@ -1419,9 +1420,53 @@
alloc_pages(msgbufpv, round_page(msgbufsize) / PAGE_SIZE);
msgbufp = (void *)msgbufpv;
+ /* Allocate space for the CPU0 CMAP */
+ bs_state.va = virtual_end;
+ pmap_bootstrap_l2_table(&bs_state);
+ pmap_store(&bs_state.l3[pmap_l3_index(bs_state.va)],
+ PHYS_TO_PTE(pmap_early_vtophys((vm_offset_t)bs_state.l3)) |
+ ATTR_AF | pmap_sh_attr | ATTR_S1_XN | ATTR_KERN_GP |
+ ATTR_S1_IDX(VM_MEMATTR_WRITE_BACK) | L3_PAGE);
+ dsb(ishst);
+
+ pc = get_pcpu();
+ mtx_init(&pc->pc_cmap_lock, "SYSMAPS", NULL, MTX_DEF);
+ pc->pc_cmap1_addr = (void *)(virtual_end + L3_SIZE);
+ pc->pc_cmap1_pte =
+ &bs_state.l3[pmap_l3_index((vm_offset_t)pc->pc_cmap1_addr)];
+
pa = pmap_early_vtophys(bs_state.freemempos);
physmem_exclude_region(start_pa, pa - start_pa, EXFLAG_NOALLOC);
+
+}
+
+void
+pmap_bootstrap_cpu(struct pcpu *pc)
+{
+ pd_entry_t *pde;
+ pt_entry_t *pte;
+ vm_offset_t addr, cmap_pte;
+ vm_paddr_t cmap_pte_pa;
+ int lvl;
+
+ addr = kva_alloc(PAGE_SIZE);
+ cmap_pte = kva_alloc(PAGE_SIZE);
+ if (addr == 0 || cmap_pte == 0)
+ panic("%s: Unable to allocate KVA", __func__);
+
+ pde = pmap_pde(kernel_pmap, addr, &lvl);
+ MPASS(lvl == 2);
+ pte = pmap_l2_to_l3(pde, addr);
+ MPASS(pmap_load(pte) == 0);
+
+ cmap_pte_pa = pmap_kextract((vm_offset_t)pte & ~L3_OFFSET);
+ pmap_kenter(cmap_pte, PAGE_SIZE, cmap_pte_pa, VM_MEMATTR_WRITE_BACK);
+
+ mtx_init(&pc->pc_cmap_lock, "SYSMAPS", NULL, MTX_DEF);
+ pc->pc_cmap1_addr = (void *)addr;
+ pc->pc_cmap1_pte = (pt_entry_t*)(cmap_pte +
+ ((vm_offset_t)pte & L3_OFFSET));
}
#if defined(KASAN) || defined(KMSAN)
diff --git a/sys/arm64/include/pcpu.h b/sys/arm64/include/pcpu.h
--- a/sys/arm64/include/pcpu.h
+++ b/sys/arm64/include/pcpu.h
@@ -35,6 +35,7 @@
#include <machine/cpu.h>
#include <machine/cpufunc.h>
+#include <machine/pte.h>
typedef int (*pcpu_bp_harden)(void);
typedef int (*pcpu_ssbd)(int);
@@ -51,7 +52,10 @@
uint64_t pc_mpidr; \
u_int pc_bcast_tlbi_workaround; \
uint64_t pc_release_addr; \
- char __pad[189]
+ struct mtx pc_cmap_lock; \
+ void *pc_cmap1_addr; \
+ pt_entry_t *pc_cmap1_pte; \
+ char __pad[145]
#ifdef _KERNEL
diff --git a/sys/arm64/include/pmap.h b/sys/arm64/include/pmap.h
--- a/sys/arm64/include/pmap.h
+++ b/sys/arm64/include/pmap.h
@@ -141,9 +141,12 @@
#define pmap_vm_page_alloc_check(m)
+struct pcpu;
+
void pmap_activate_vm(pmap_t);
void pmap_bootstrap_dmap(vm_size_t);
void pmap_bootstrap(void);
+void pmap_bootstrap_cpu(struct pcpu *);
int pmap_change_attr(vm_offset_t va, vm_size_t size, int mode);
int pmap_change_prot(vm_offset_t va, vm_size_t size, vm_prot_t prot);
void pmap_kenter(vm_offset_t sva, vm_size_t size, vm_paddr_t pa, int mode);

File Metadata

Mime Type
text/plain
Expires
Mon, Apr 20, 9:32 AM (9 h, 21 m)
Storage Engine
blob
Storage Format
Raw Data
Storage Handle
31786298
Default Alt Text
D56306.id175102.diff (3 KB)

Event Timeline