Source-Changes-HG archive

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index][Old Index]

[src/netbsd-8]: src/sys/arch Pull up the following revisions (via patch), req...



details:   https://anonhg.NetBSD.org/src/rev/09c049d55c6b
branches:  netbsd-8
changeset: 851484:09c049d55c6b
user:      martin <martin%NetBSD.org@localhost>
date:      Fri Mar 16 13:17:56 2018 +0000

description:
Pull up the following revisions (via patch), requested by maxv in #635:

        sys/arch/amd64/amd64/gdt.c              1.39-1.45 (patch)
        sys/arch/amd64/amd64/amd64/machdep.c    1.284,1.287,1.288 (patch)
        sys/arch/amd64/amd64/include/param.h    1.23 (patch)
        sys/arch/amd64/include/types.h          1.53 (patch)
        sys/arch/x86/include/cpu.h              1.87 (patch)
        sys/arch/x86/include/pmap.h             1.73,1.74 (patch)
        sys/arch/x86/x86/cpu.c                  1.142 (patch)
        sys/arch/x86/x86/intr.c                 1.117 (partial),1.120 (patch)
        sys/arch/x86/x86/pmap.c                 1.276 (patch)

Initialize ist0 in cpu_init_tss.
Backport __HAVE_PCPU_AREA.

diffstat:

 sys/arch/amd64/amd64/gdt.c     |  138 ++++++++++++++--------------------------
 sys/arch/amd64/amd64/machdep.c |   35 ++++++++-
 sys/arch/amd64/include/param.h |    3 +-
 sys/arch/amd64/include/types.h |    3 +-
 sys/arch/x86/include/cpu.h     |    4 +-
 sys/arch/x86/include/pmap.h    |   33 +++++++++-
 sys/arch/x86/x86/cpu.c         |   37 ++++++++++-
 sys/arch/x86/x86/intr.c        |   27 ++++---
 sys/arch/x86/x86/pmap.c        |  121 +++++++++++++++++++++++++++++++++++-
 9 files changed, 287 insertions(+), 114 deletions(-)

diffs (truncated from 774 to 300 lines):

diff -r 5f457e0ecd26 -r 09c049d55c6b sys/arch/amd64/amd64/gdt.c
--- a/sys/arch/amd64/amd64/gdt.c        Fri Mar 16 13:08:14 2018 +0000
+++ b/sys/arch/amd64/amd64/gdt.c        Fri Mar 16 13:17:56 2018 +0000
@@ -1,6 +1,6 @@
-/*     $NetBSD: gdt.c,v 1.38 2017/03/25 15:05:16 maxv Exp $    */
+/*     $NetBSD: gdt.c,v 1.38.6.1 2018/03/16 13:17:56 martin Exp $      */
 
-/*-
+/*
  * Copyright (c) 1996, 1997, 2009 The NetBSD Foundation, Inc.
  * All rights reserved.
  *
@@ -37,7 +37,7 @@
  */
 
 #include <sys/cdefs.h>
-__KERNEL_RCSID(0, "$NetBSD: gdt.c,v 1.38 2017/03/25 15:05:16 maxv Exp $");
+__KERNEL_RCSID(0, "$NetBSD: gdt.c,v 1.38.6.1 2018/03/16 13:17:56 martin Exp $");
 
 #include "opt_multiprocessor.h"
 #include "opt_xen.h"
@@ -57,16 +57,24 @@
 #include <xen/hypervisor.h>
 #endif
 
-#define NDYNSLOTS \
-       ((MAXGDTSIZ - DYNSEL_START) / sizeof(struct sys_segment_descriptor))
+#define NSLOTS(sz)     \
+       (((sz) - DYNSEL_START) / sizeof(struct sys_segment_descriptor))
+#define NDYNSLOTS      NSLOTS(MAXGDTSIZ)
 
 typedef struct {
        bool busy[NDYNSLOTS];
        size_t nslots;
 } gdt_bitmap_t;
 
-size_t gdt_size;                       /* size of GDT in bytes */              
-static gdt_bitmap_t gdt_bitmap;                /* bitmap of busy slots */
+/* size of GDT in bytes */
+#ifdef XEN
+const size_t gdt_size = FIRST_RESERVED_GDT_BYTE;
+#else
+const size_t gdt_size = MAXGDTSIZ;
+#endif
+
+/* bitmap of busy slots */
+static gdt_bitmap_t gdt_bitmap;
 
 #if defined(USER_LDT) || !defined(XEN)
 static void set_sys_gdt(int, void *, size_t, int, int, int);
@@ -124,27 +132,25 @@
 gdt_init(void)
 {
        char *old_gdt;
-       struct vm_page *pg;
-       vaddr_t va;
        struct cpu_info *ci = &cpu_info_primary;
 
        /* Initialize the global values */
-       gdt_size = MINGDTSIZ;
        memset(&gdt_bitmap.busy, 0, sizeof(gdt_bitmap.busy));
-       gdt_bitmap.nslots =
-           (gdt_size - DYNSEL_START) / sizeof(struct sys_segment_descriptor);
+       gdt_bitmap.nslots = NSLOTS(gdt_size);
 
        old_gdt = gdtstore;
 
-       /* Allocate MAXGDTSIZ bytes of virtual memory. */
-       gdtstore = (char *)uvm_km_alloc(kernel_map, MAXGDTSIZ, 0,
-           UVM_KMF_VAONLY);
+#ifdef __HAVE_PCPU_AREA
+       /* The GDT is part of the pcpuarea */
+       gdtstore = (char *)&pcpuarea->ent[cpu_index(ci)].gdt;
+#else
+       struct vm_page *pg;
+       vaddr_t va;
 
-       /*
-        * Allocate only MINGDTSIZ bytes of physical memory. We will grow this
-        * area in gdt_grow at run-time if needed.
-        */
-       for (va = (vaddr_t)gdtstore; va < (vaddr_t)gdtstore + MINGDTSIZ;
+       /* Allocate gdt_size bytes of memory. */
+       gdtstore = (char *)uvm_km_alloc(kernel_map, gdt_size, 0,
+           UVM_KMF_VAONLY);
+       for (va = (vaddr_t)gdtstore; va < (vaddr_t)gdtstore + gdt_size;
            va += PAGE_SIZE) {
                pg = uvm_pagealloc(NULL, 0, NULL, UVM_PGA_ZERO);
                if (pg == NULL) {
@@ -154,6 +160,7 @@
                    VM_PROT_READ | VM_PROT_WRITE, 0);
        }
        pmap_update(pmap_kernel());
+#endif
 
        /* Copy the initial bootstrap GDT into the new area. */
        memcpy(gdtstore, old_gdt, DYNSEL_START);
@@ -173,15 +180,15 @@
 void
 gdt_alloc_cpu(struct cpu_info *ci)
 {
-       int max_len = MAXGDTSIZ;
-       int min_len = MINGDTSIZ;
+#ifdef __HAVE_PCPU_AREA
+       ci->ci_gdt = (union descriptor *)&pcpuarea->ent[cpu_index(ci)].gdt;
+#else
        struct vm_page *pg;
        vaddr_t va;
 
-       ci->ci_gdt = (union descriptor *)uvm_km_alloc(kernel_map, max_len,
+       ci->ci_gdt = (union descriptor *)uvm_km_alloc(kernel_map, gdt_size,
            0, UVM_KMF_VAONLY);
-
-       for (va = (vaddr_t)ci->ci_gdt; va < (vaddr_t)ci->ci_gdt + min_len;
+       for (va = (vaddr_t)ci->ci_gdt; va < (vaddr_t)ci->ci_gdt + gdt_size;
            va += PAGE_SIZE) {
                while ((pg = uvm_pagealloc(NULL, 0, NULL, UVM_PGA_ZERO))
                    == NULL) {
@@ -191,8 +198,8 @@
                    VM_PROT_READ | VM_PROT_WRITE, 0);
        }
        pmap_update(pmap_kernel());
+#endif
 
-       memset(ci->ci_gdt, 0, min_len);
        memcpy(ci->ci_gdt, gdtstore, gdt_size);
 }
 
@@ -207,52 +214,11 @@
 
        KASSERT(curcpu() == ci);
 
-#ifndef XEN
-       setregion(&region, ci->ci_gdt, (uint16_t)(MAXGDTSIZ - 1));
-#else
        setregion(&region, ci->ci_gdt, (uint16_t)(gdt_size - 1));
-#endif
        lgdt(&region);
 }
 
 #if !defined(XEN) || defined(USER_LDT)
-/*
- * Grow the GDT. The GDT is present on each CPU, so we need to iterate over all
- * of them. We already have the virtual memory, we only need to grow the
- * physical memory.
- */
-static void
-gdt_grow(void)
-{
-       size_t old_size;
-       CPU_INFO_ITERATOR cii;
-       struct cpu_info *ci;
-       struct vm_page *pg;
-       vaddr_t va;
-
-       old_size = gdt_size;
-       gdt_size *= 2;
-       if (gdt_size > MAXGDTSIZ)
-               gdt_size = MAXGDTSIZ;
-       gdt_bitmap.nslots =
-           (gdt_size - DYNSEL_START) / sizeof(struct sys_segment_descriptor);
-
-       for (CPU_INFO_FOREACH(cii, ci)) {
-               for (va = (vaddr_t)(ci->ci_gdt) + old_size;
-                    va < (vaddr_t)(ci->ci_gdt) + gdt_size;
-                    va += PAGE_SIZE) {
-                       while ((pg = uvm_pagealloc(NULL, 0, NULL, UVM_PGA_ZERO)) ==
-                           NULL) {
-                               uvm_wait("gdt_grow");
-                       }
-                       pmap_kenter_pa(va, VM_PAGE_TO_PHYS(pg),
-                           VM_PROT_READ | VM_PROT_WRITE, 0);
-               }
-       }
-
-       pmap_update(pmap_kernel());
-}
-
 static int
 gdt_get_slot(void)
 {
@@ -260,17 +226,14 @@
 
        KASSERT(mutex_owned(&cpu_lock));
 
-       while (1) {
-               for (i = 0; i < gdt_bitmap.nslots; i++) {
-                       if (!gdt_bitmap.busy[i]) {
-                               gdt_bitmap.busy[i] = true;
-                               return (int)i;
-                       }
+       for (i = 0; i < gdt_bitmap.nslots; i++) {
+               if (!gdt_bitmap.busy[i]) {
+                       gdt_bitmap.busy[i] = true;
+                       return (int)i;
                }
-               if (gdt_size >= MAXGDTSIZ)
-                       panic("gdt_get_slot: out of memory");
-               gdt_grow();
        }
+       panic("gdt_get_slot: out of memory");
+
        /* NOTREACHED */
        return 0;
 }
@@ -349,26 +312,25 @@
 lgdt(struct region_descriptor *desc)
 {
        paddr_t frames[16];
-       int i;
+       size_t i;
        vaddr_t va;
 
        /*
-        * XXX: Xen even checks descriptors AFTER limit.
-        * Zero out last frame after limit if needed.
+        * Xen even checks descriptors AFTER limit. Zero out last frame after
+        * limit if needed.
         */
        va = desc->rd_base + desc->rd_limit + 1;
        memset((void *)va, 0, roundup(va, PAGE_SIZE) - va);
+
+       /*
+        * The lgdt instruction uses virtual addresses, do some translation for
+        * Xen. Mark pages R/O too, otherwise Xen will refuse to use them.
+        */
        for (i = 0; i < roundup(desc->rd_limit, PAGE_SIZE) >> PAGE_SHIFT; i++) {
-               /*
-                * The lgdt instruction uses virtual addresses,
-                * do some translation for Xen.
-                * Mark pages R/O too, else Xen will refuse to use them.
-                */
-               frames[i] = ((paddr_t) xpmap_ptetomach(
-                   (pt_entry_t *)(desc->rd_base + (i << PAGE_SHIFT)))) >>
+               va = desc->rd_base + (i << PAGE_SHIFT);
+               frames[i] = ((paddr_t)xpmap_ptetomach((pt_entry_t *)va)) >>
                    PAGE_SHIFT;
-               pmap_pte_clearbits(kvtopte(desc->rd_base + (i << PAGE_SHIFT)),
-                   PG_RW);
+               pmap_pte_clearbits(kvtopte(va), PG_RW);
        }
 
        if (HYPERVISOR_set_gdt(frames, (desc->rd_limit + 1) >> 3))
diff -r 5f457e0ecd26 -r 09c049d55c6b sys/arch/amd64/amd64/machdep.c
--- a/sys/arch/amd64/amd64/machdep.c    Fri Mar 16 13:08:14 2018 +0000
+++ b/sys/arch/amd64/amd64/machdep.c    Fri Mar 16 13:17:56 2018 +0000
@@ -1,4 +1,4 @@
-/*     $NetBSD: machdep.c,v 1.255.6.4 2018/03/13 15:47:44 martin Exp $ */
+/*     $NetBSD: machdep.c,v 1.255.6.5 2018/03/16 13:17:56 martin Exp $ */
 
 /*-
  * Copyright (c) 1996, 1997, 1998, 2000, 2006, 2007, 2008, 2011
@@ -111,7 +111,7 @@
  */
 
 #include <sys/cdefs.h>
-__KERNEL_RCSID(0, "$NetBSD: machdep.c,v 1.255.6.4 2018/03/13 15:47:44 martin Exp $");
+__KERNEL_RCSID(0, "$NetBSD: machdep.c,v 1.255.6.5 2018/03/16 13:17:56 martin Exp $");
 
 /* #define XENDEBUG_LOW  */
 
@@ -391,6 +391,9 @@
        x86_bus_space_mallocok();
 #endif
 
+#ifdef __HAVE_PCPU_AREA
+       cpu_pcpuarea_init(&cpu_info_primary);
+#endif
        gdt_init();
        x86_64_proc0_tss_ldt_init();
 
@@ -500,21 +503,43 @@
 void
 cpu_init_tss(struct cpu_info *ci)
 {
+#ifdef __HAVE_PCPU_AREA
+       const cpuid_t cid = cpu_index(ci);
+#endif
        struct cpu_tss *cputss;
        uintptr_t p;
 
+#ifdef __HAVE_PCPU_AREA
+       cputss = (struct cpu_tss *)&pcpuarea->ent[cid].tss;
+#else
        cputss = (struct cpu_tss *)uvm_km_alloc(kernel_map,
            sizeof(struct cpu_tss), 0, UVM_KMF_WIRED|UVM_KMF_ZERO);
+#endif
 
        cputss->tss.tss_iobase = IOMAP_INVALOFF << 16;
-       /* cputss->tss.tss_ist[0] is filled by cpu_intr_init */
+
+       /* DDB stack */
+#ifdef __HAVE_PCPU_AREA
+       p = (vaddr_t)&pcpuarea->ent[cid].ist0;
+#else
+       p = uvm_km_alloc(kernel_map, PAGE_SIZE, 0, UVM_KMF_WIRED|UVM_KMF_ZERO);
+#endif
+       cputss->tss.tss_ist[0] = p + PAGE_SIZE - 16;
 
        /* double fault */



Home | Main Index | Thread Index | Old Index