svn commit: r216960 - head/sys/i386/xen

Colin Percival cperciva at FreeBSD.org
Tue Jan 4 15:55:16 UTC 2011


Author: cperciva
Date: Tue Jan  4 15:55:15 2011
New Revision: 216960
URL: http://svn.freebsd.org/changeset/base/216960

Log:
  Add hamfisted locking to the Xen/PV pmap code: Only allow one thread to
  be in {pmap_pinit, pmap_copy, pmap_release} at a time.
  
  This reduces the rate of panics when running 'make index' from ~0.6/hour
  to ~0.02/hour (p < 10^-30).
  
  At a later date this locking will be removed, and for this reason, it is
  wrapped in #ifdef HAMFISTED_LOCKING; this temporary hack is being put in
  place with the intention of shipping somewhat-stable Xen bits in FreeBSD
  8.2-RELEASE.
  
  PR:		kern/153672
  MFC after:	3 days

Modified:
  head/sys/i386/xen/pmap.c

Modified: head/sys/i386/xen/pmap.c
==============================================================================
--- head/sys/i386/xen/pmap.c	Tue Jan  4 15:53:38 2011	(r216959)
+++ head/sys/i386/xen/pmap.c	Tue Jan  4 15:55:15 2011	(r216960)
@@ -202,6 +202,11 @@ __FBSDID("$FreeBSD$");
 
 #define pmap_pte_set_prot(pte, v) ((*(int *)pte &= ~PG_PROT), (*(int *)pte |= (v)))
 
+#define HAMFISTED_LOCKING
+#ifdef HAMFISTED_LOCKING
+static struct mtx createdelete_lock;
+#endif
+
 struct pmap kernel_pmap_store;
 LIST_HEAD(pmaplist, pmap);
 static struct pmaplist allpmaps;
@@ -502,6 +507,10 @@ pmap_bootstrap(vm_paddr_t firstaddr)
 	/* Turn on PG_G on kernel page(s) */
 	pmap_set_pg();
 #endif
+
+#ifdef HAMFISTED_LOCKING
+	mtx_init(&createdelete_lock, "pmap create/delete", NULL, MTX_DEF);
+#endif
 }
 
 /*
@@ -1462,6 +1471,10 @@ pmap_pinit(pmap_t pmap)
 	static int color;
 	int i;
 
+#ifdef HAMFISTED_LOCKING
+	mtx_lock(&createdelete_lock);
+#endif
+
 	PMAP_LOCK_INIT(pmap);
 
 	/*
@@ -1473,6 +1486,9 @@ pmap_pinit(pmap_t pmap)
 		    NBPTD);
 		if (pmap->pm_pdir == NULL) {
 			PMAP_LOCK_DESTROY(pmap);
+#ifdef HAMFISTED_LOCKING
+			mtx_unlock(&createdelete_lock);
+#endif
 			return (0);
 		}
 #ifdef PAE
@@ -1545,6 +1561,9 @@ pmap_pinit(pmap_t pmap)
 	TAILQ_INIT(&pmap->pm_pvchunk);
 	bzero(&pmap->pm_stats, sizeof pmap->pm_stats);
 
+#ifdef HAMFISTED_LOCKING
+	mtx_unlock(&createdelete_lock);
+#endif
 	return (1);
 }
 
@@ -1776,6 +1795,10 @@ pmap_release(pmap_t pmap)
 	    pmap->pm_stats.resident_count));
 	PT_UPDATES_FLUSH();
 
+#ifdef HAMFISTED_LOCKING
+	mtx_lock(&createdelete_lock);
+#endif
+
 	pmap_lazyfix(pmap);
 	mtx_lock_spin(&allpmaps_lock);
 	LIST_REMOVE(pmap, pm_list);
@@ -1811,6 +1834,10 @@ pmap_release(pmap_t pmap)
 	pmap_qremove((vm_offset_t)pmap->pm_pdpt, 1);
 #endif
 	PMAP_LOCK_DESTROY(pmap);
+
+#ifdef HAMFISTED_LOCKING
+	mtx_unlock(&createdelete_lock);
+#endif
 }
 
 static int
@@ -3136,6 +3163,10 @@ pmap_copy(pmap_t dst_pmap, pmap_t src_pm
 	CTR5(KTR_PMAP, "pmap_copy:  dst_pmap=%p src_pmap=%p dst_addr=0x%x len=%d src_addr=0x%x",
 	    dst_pmap, src_pmap, dst_addr, len, src_addr);
 	
+#ifdef HAMFISTED_LOCKING
+	mtx_lock(&createdelete_lock);
+#endif
+
 	vm_page_lock_queues();
 	if (dst_pmap < src_pmap) {
 		PMAP_LOCK(dst_pmap);
@@ -3225,6 +3256,10 @@ pmap_copy(pmap_t dst_pmap, pmap_t src_pm
 	vm_page_unlock_queues();
 	PMAP_UNLOCK(src_pmap);
 	PMAP_UNLOCK(dst_pmap);
+
+#ifdef HAMFISTED_LOCKING
+	mtx_unlock(&createdelete_lock);
+#endif
 }	
 
 static __inline void


More information about the svn-src-all mailing list