Module Name: src Committed By: riz Date: Thu Jul 5 18:39:42 UTC 2012
Modified Files: src/sys/arch/mips/include [netbsd-6]: pmap.h src/sys/arch/mips/mips [netbsd-6]: pmap.c pmap_segtab.c Log Message: Pull up following revision(s) (requested by matt in ticket #406): sys/arch/mips/include/pmap.h: revision 1.62 sys/arch/mips/mips/pmap.c: revision 1.208 sys/arch/mips/mips/pmap_segtab.c: revision 1.5 Change lockless segtab management to use a mutex for protection. Some = minor changes to make this closer to common/pmap/tlb/pmap_segtab.c =20 =20 To generate a diff of this commit: cvs rdiff -u -r1.61 -r1.61.8.1 src/sys/arch/mips/include/pmap.h cvs rdiff -u -r1.207 -r1.207.2.1 src/sys/arch/mips/mips/pmap.c cvs rdiff -u -r1.4 -r1.4.2.1 src/sys/arch/mips/mips/pmap_segtab.c Please note that diffs are not public domain; they are subject to the copyright notices on the relevant files.
Modified files: Index: src/sys/arch/mips/include/pmap.h diff -u src/sys/arch/mips/include/pmap.h:1.61 src/sys/arch/mips/include/pmap.h:1.61.8.1 --- src/sys/arch/mips/include/pmap.h:1.61 Thu Sep 22 05:08:52 2011 +++ src/sys/arch/mips/include/pmap.h Thu Jul 5 18:39:42 2012 @@ -1,4 +1,4 @@ -/* $NetBSD: pmap.h,v 1.61 2011/09/22 05:08:52 macallan Exp $ */ +/* $NetBSD: pmap.h,v 1.61.8.1 2012/07/05 18:39:42 riz Exp $ */ /* * Copyright (c) 1992, 1993 @@ -148,6 +148,7 @@ void pmap_pte_process(struct pmap *, vad void pmap_segtab_activate(struct pmap *, struct lwp *); void pmap_segtab_init(struct pmap *); void pmap_segtab_destroy(struct pmap *); +extern kmutex_t pmap_segtab_lock; #endif /* _KERNEL */ /* Index: src/sys/arch/mips/mips/pmap.c diff -u src/sys/arch/mips/mips/pmap.c:1.207 src/sys/arch/mips/mips/pmap.c:1.207.2.1 --- src/sys/arch/mips/mips/pmap.c:1.207 Thu Feb 2 18:59:44 2012 +++ src/sys/arch/mips/mips/pmap.c Thu Jul 5 18:39:42 2012 @@ -1,4 +1,4 @@ -/* $NetBSD: pmap.c,v 1.207 2012/02/02 18:59:44 para Exp $ */ +/* $NetBSD: pmap.c,v 1.207.2.1 2012/07/05 18:39:42 riz Exp $ */ /*- * Copyright (c) 1998, 2001 The NetBSD Foundation, Inc. @@ -67,7 +67,7 @@ #include <sys/cdefs.h> -__KERNEL_RCSID(0, "$NetBSD: pmap.c,v 1.207 2012/02/02 18:59:44 para Exp $"); +__KERNEL_RCSID(0, "$NetBSD: pmap.c,v 1.207.2.1 2012/07/05 18:39:42 riz Exp $"); /* * Manages physical address maps. @@ -276,8 +276,8 @@ struct pmap * const kernel_pmap_ptr = &k paddr_t mips_avail_start; /* PA of first available physical page */ paddr_t mips_avail_end; /* PA of last available physical page */ vaddr_t mips_virtual_end; /* VA of last avail page (end of kernel AS) */ -vaddr_t iospace; /* VA of start of I/O space, if needed */ -vsize_t iospace_size = 0; /* Size of (initial) range of I/O addresses */ +vaddr_t iospace; /* VA of start of I/O space, if needed */ +vsize_t iospace_size = 0; /* Size of (initial) range of I/O addresses */ pt_entry_t *Sysmap; /* kernel pte table */ unsigned int Sysmapsize; /* number of pte's in Sysmap */ @@ -739,6 +739,11 @@ pmap_init(void) #endif /* + * Initialize the segtab lock. + */ + mutex_init(&pmap_segtab_lock, MUTEX_DEFAULT, IPL_HIGH); + + /* * Set a low water mark on the pv_entry pool, so that we are * more likely to have these around even in extreme memory * starvation. @@ -2108,11 +2113,11 @@ pmap_enter_pv(pmap_t pmap, vaddr_t va, s pv_entry_t pv, npv, apv; int16_t gen; - KASSERT(kpreempt_disabled()); - KASSERT(!MIPS_KSEG0_P(va)); - KASSERT(!MIPS_KSEG1_P(va)); + KASSERT(kpreempt_disabled()); + KASSERT(!MIPS_KSEG0_P(va)); + KASSERT(!MIPS_KSEG1_P(va)); #ifdef _LP64 - KASSERT(!MIPS_XKPHYS_P(va)); + KASSERT(!MIPS_XKPHYS_P(va)); #endif apv = NULL; Index: src/sys/arch/mips/mips/pmap_segtab.c diff -u src/sys/arch/mips/mips/pmap_segtab.c:1.4 src/sys/arch/mips/mips/pmap_segtab.c:1.4.2.1 --- src/sys/arch/mips/mips/pmap_segtab.c:1.4 Thu Jan 26 02:14:08 2012 +++ src/sys/arch/mips/mips/pmap_segtab.c Thu Jul 5 18:39:42 2012 @@ -1,4 +1,4 @@ -/* $NetBSD: pmap_segtab.c,v 1.4 2012/01/26 02:14:08 matt Exp $ */ +/* $NetBSD: pmap_segtab.c,v 1.4.2.1 2012/07/05 18:39:42 riz Exp $ */ /*- * Copyright (c) 1998, 2001 The NetBSD Foundation, Inc. @@ -67,7 +67,7 @@ #include <sys/cdefs.h> -__KERNEL_RCSID(0, "$NetBSD: pmap_segtab.c,v 1.4 2012/01/26 02:14:08 matt Exp $"); +__KERNEL_RCSID(0, "$NetBSD: pmap_segtab.c,v 1.4.2.1 2012/07/05 18:39:42 riz Exp $"); /* * Manages physical address maps. @@ -119,13 +119,8 @@ __KERNEL_RCSID(0, "$NetBSD: pmap_segtab. #include <sys/param.h> #include <sys/systm.h> #include <sys/proc.h> -#include <sys/pool.h> #include <sys/mutex.h> #include <sys/atomic.h> -#ifdef SYSVSHM -#include <sys/shm.h> -#endif -#include <sys/socketvar.h> /* XXX: for sock_loan_thresh */ #include <uvm/uvm.h> @@ -136,15 +131,19 @@ __KERNEL_RCSID(0, "$NetBSD: pmap_segtab. CTASSERT(NBPG >= sizeof(union segtab)); -union segtab * volatile free_segtab; /* free list kept locally */ +struct pmap_segtab_info { + union segtab *free_segtab; /* free list kept locally */ #ifdef DEBUG -uint32_t nget_segtab; -uint32_t nput_segtab; -uint32_t npage_segtab; -#define SEGTAB_ADD(n, v) (n ## _segtab += (v)) + uint32_t nget_segtab; + uint32_t nput_segtab; + uint32_t npage_segtab; +#define SEGTAB_ADD(n, v) (pmap_segtab_info.n ## _segtab += (v)) #else #define SEGTAB_ADD(n, v) ((void) 0) #endif +} pmap_segtab_info; + +kmutex_t pmap_segtab_lock __cacheline_aligned; static inline struct vm_page * pmap_pte_pagealloc(void) @@ -184,14 +183,11 @@ pmap_segtab_free(union segtab *stp) /* * Insert the the segtab into the segtab freelist. */ - for (;;) { - void *tmp = free_segtab; - stp->seg_tab[0] = tmp; - if (tmp == atomic_cas_ptr(&free_segtab, tmp, stp)) { - SEGTAB_ADD(nput, 1); - break; - } - } + mutex_spin_enter(&pmap_segtab_lock); + stp->seg_tab[0] = (void *) pmap_segtab_info.free_segtab; + pmap_segtab_info.free_segtab = stp; + SEGTAB_ADD(nput, 1); + mutex_spin_exit(&pmap_segtab_lock); } static void @@ -261,21 +257,18 @@ static union segtab * pmap_segtab_alloc(void) { union segtab *stp; + again: - stp = NULL; - while (__predict_true(free_segtab != NULL)) { - union segtab *next_stp; - stp = free_segtab; - next_stp = (union segtab *)stp->seg_tab[0]; - if (stp == atomic_cas_ptr(&free_segtab, stp, next_stp)) { - SEGTAB_ADD(nget, 1); - break; - } - } - - if (__predict_true(stp != NULL)) { + mutex_spin_enter(&pmap_segtab_lock); + if (__predict_true((stp = pmap_segtab_info.free_segtab) != NULL)) { + pmap_segtab_info.free_segtab = + (union segtab *)stp->seg_tab[0]; stp->seg_tab[0] = NULL; - } else { + SEGTAB_ADD(nget, 1); + } + mutex_spin_exit(&pmap_segtab_lock); + + if (__predict_false(stp == NULL)) { struct vm_page * const stp_pg = pmap_pte_pagealloc(); if (__predict_false(stp_pg == NULL)) { @@ -292,7 +285,7 @@ pmap_segtab_alloc(void) KASSERT(mips_options.mips3_xkphys_cached); #endif stp = (union segtab *)mips_pmap_map_poolpage(stp_pa); - const size_t n = NBPG / sizeof(union segtab); + const size_t n = NBPG / sizeof(*stp); if (n > 1) { /* * link all the segtabs in this page together @@ -303,13 +296,11 @@ pmap_segtab_alloc(void) /* * Now link the new segtabs into the free segtab list. */ - for (;;) { - void *tmp = free_segtab; - stp[n-1].seg_tab[0] = tmp; - if (tmp == atomic_cas_ptr(&free_segtab, tmp, stp+1)) - break; - } + mutex_spin_enter(&pmap_segtab_lock); + stp[n-1].seg_tab[0] = (void *)pmap_segtab_info.free_segtab; + pmap_segtab_info.free_segtab = stp + 1; SEGTAB_ADD(nput, n - 1); + mutex_spin_exit(&pmap_segtab_lock); } } @@ -433,7 +424,7 @@ pmap_pte_reserve(pmap_t pmap, vaddr_t va union segtab *ostp = atomic_cas_ptr(stp_p, NULL, nstp); if (__predict_false(ostp != NULL)) { pmap_segtab_free(nstp); - stp = ostp; + nstp = ostp; } #else *stp_p = nstp;