Module Name:    src
Committed By:   uebayasi
Date:           Mon Nov 15 17:32:02 UTC 2010

Modified Files:
        src/sys/miscfs/genfs [uebayasi-xip]: genfs_io.c
        src/sys/uvm [uebayasi-xip]: uvm_page.c uvm_page.h

Log Message:
Move zero-page into a common place, in the hope that it's shared
for other purposes.

According to Chuck Silvers, zero-page mappings don't need to be
explicitly unmapped in putpages().  Follow that advice.


To generate a diff of this commit:
cvs rdiff -u -r1.36.2.30 -r1.36.2.31 src/sys/miscfs/genfs/genfs_io.c
cvs rdiff -u -r1.153.2.64 -r1.153.2.65 src/sys/uvm/uvm_page.c
cvs rdiff -u -r1.59.2.35 -r1.59.2.36 src/sys/uvm/uvm_page.h

Please note that diffs are not public domain; they are subject to the
copyright notices on the relevant files.

Modified files:

Index: src/sys/miscfs/genfs/genfs_io.c
diff -u src/sys/miscfs/genfs/genfs_io.c:1.36.2.30 src/sys/miscfs/genfs/genfs_io.c:1.36.2.31
--- src/sys/miscfs/genfs/genfs_io.c:1.36.2.30	Sat Nov  6 08:08:44 2010
+++ src/sys/miscfs/genfs/genfs_io.c	Mon Nov 15 17:32:01 2010
@@ -1,4 +1,4 @@
-/*	$NetBSD: genfs_io.c,v 1.36.2.30 2010/11/06 08:08:44 uebayasi Exp $	*/
+/*	$NetBSD: genfs_io.c,v 1.36.2.31 2010/11/15 17:32:01 uebayasi Exp $	*/
 
 /*
  * Copyright (c) 1982, 1986, 1989, 1993
@@ -31,7 +31,7 @@
  */
 
 #include <sys/cdefs.h>
-__KERNEL_RCSID(0, "$NetBSD: genfs_io.c,v 1.36.2.30 2010/11/06 08:08:44 uebayasi Exp $");
+__KERNEL_RCSID(0, "$NetBSD: genfs_io.c,v 1.36.2.31 2010/11/15 17:32:01 uebayasi Exp $");
 
 #include "opt_xip.h"
 
@@ -873,18 +873,8 @@
 		 *   allocated and linearly ordered by physical address.
 		 */
 		if (blkno < 0) {
-			zero_page = uvm_pagelookup(uobj, 0);
-
-			if (zero_page == NULL) {
-				mutex_enter(&uobj->vmobjlock);
-				zero_page = uvm_pagealloc(uobj, 0, NULL,
-				    UVM_PGA_ZERO);
-				mutex_exit(&uobj->vmobjlock);
-				KASSERT(zero_page != NULL);
-				mutex_enter(&uvm_pageqlock);
-				uvm_pagewire(zero_page);
-				mutex_exit(&uvm_pageqlock);
-			}
+			zero_page = uvm_page_zeropage_alloc();
+			KASSERT(zero_page != NULL);
 			pps[i] = zero_page;
 		} else {
 			struct vm_physseg *seg;
@@ -918,10 +908,10 @@
 	for (i = 0; i < npages; i++) {
 		struct vm_page *pg = pps[i];
 
+		KASSERT((pg->flags & PG_RDONLY) != 0);
 		if (pg == zero_page) {
 		} else {
 			KASSERT((pg->flags & PG_BUSY) == 0);
-			KASSERT((pg->flags & PG_RDONLY) != 0);
 			KASSERT((pg->flags & PG_CLEAN) != 0);
 			KASSERT((pg->flags & PG_DEVICE) != 0);
 			pg->flags |= PG_BUSY;
@@ -1544,8 +1534,8 @@
 			pg = pgs[i];
 			if (pg == NULL || pg == PGO_DONTCARE)
 				continue;
-			if (pg == zero_page) {
-				put_zero_page = true;
+			if (pg == uvm_page_zeropage) {
+				/* Do nothing for holes. */
 			} else {
 				/*
 				 * Freeing normal XIP pages; nothing to do.
@@ -1562,17 +1552,6 @@
 		off += npages << PAGE_SHIFT;
 	}
 
-	if (put_zero_page) {
-		/*
-		 * Freeing an XIP zero page.
-		 */
-		pmap_page_protect(zero_page, VM_PROT_NONE);
-		mutex_enter(&uvm_pageqlock);
-		uvm_pageunwire(zero_page);
-		mutex_exit(&uvm_pageqlock);
-		uvm_pagefree(zero_page);
-	}
-
 	KASSERT(uobj->uo_npages == 0);
 
 done:

Index: src/sys/uvm/uvm_page.c
diff -u src/sys/uvm/uvm_page.c:1.153.2.64 src/sys/uvm/uvm_page.c:1.153.2.65
--- src/sys/uvm/uvm_page.c:1.153.2.64	Fri Nov 12 19:02:44 2010
+++ src/sys/uvm/uvm_page.c	Mon Nov 15 17:32:01 2010
@@ -1,4 +1,4 @@
-/*	$NetBSD: uvm_page.c,v 1.153.2.64 2010/11/12 19:02:44 uebayasi Exp $	*/
+/*	$NetBSD: uvm_page.c,v 1.153.2.65 2010/11/15 17:32:01 uebayasi Exp $	*/
 
 /*
  * Copyright (c) 2010 The NetBSD Foundation, Inc.
@@ -97,7 +97,7 @@
  */
 
 #include <sys/cdefs.h>
-__KERNEL_RCSID(0, "$NetBSD: uvm_page.c,v 1.153.2.64 2010/11/12 19:02:44 uebayasi Exp $");
+__KERNEL_RCSID(0, "$NetBSD: uvm_page.c,v 1.153.2.65 2010/11/15 17:32:01 uebayasi Exp $");
 
 #include "opt_ddb.h"
 #include "opt_uvmhist.h"
@@ -113,6 +113,7 @@
 #include <sys/proc.h>
 #include <sys/atomic.h>
 #include <sys/cpu.h>
+#include <sys/once.h>
 
 #include <uvm/uvm.h>
 #include <uvm/uvm_ddb.h>
@@ -2234,6 +2235,46 @@
 	return (VM_PHYSMEM_PTR(lcv)->free_list);
 }
 
+static int uvm_page_zeropage_init(void);
+
+struct vm_page *uvm_page_zeropage;
+
+struct vm_page *
+uvm_page_zeropage_alloc(void)
+{
+	static ONCE_DECL(inited);
+
+	(void)RUN_ONCE(&inited, uvm_page_zeropage_init);
+	KASSERT(uvm_page_zeropage != NULL);
+	return uvm_page_zeropage;
+}
+
+static int
+uvm_page_zeropage_init(void)
+{
+	struct pglist mlist;
+	struct vm_page *pg;
+	int n;
+
+	n = uvm_pglistalloc(PAGE_SIZE, 0, -1, PAGE_SIZE, PAGE_SIZE,
+	    &mlist, 1, 1);
+	KASSERT(n == 1);
+
+	pg = TAILQ_FIRST(&mlist);
+	KASSERT(pg != NULL);
+
+	pmap_zero_page(VM_PAGE_TO_PHYS(pg));
+
+	pg->flags |= PG_RDONLY;
+
+	mutex_enter(&uvm_pageqlock);
+	uvm_pagewire(pg);
+	mutex_exit(&uvm_pageqlock);
+
+	uvm_page_zeropage = pg;
+	return 0;
+}
+
 #if defined(DDB) || defined(DEBUGPRINT)
 
 /*

Index: src/sys/uvm/uvm_page.h
diff -u src/sys/uvm/uvm_page.h:1.59.2.35 src/sys/uvm/uvm_page.h:1.59.2.36
--- src/sys/uvm/uvm_page.h:1.59.2.35	Fri Nov 12 08:13:40 2010
+++ src/sys/uvm/uvm_page.h	Mon Nov 15 17:32:01 2010
@@ -1,4 +1,4 @@
-/*	$NetBSD: uvm_page.h,v 1.59.2.35 2010/11/12 08:13:40 uebayasi Exp $	*/
+/*	$NetBSD: uvm_page.h,v 1.59.2.36 2010/11/15 17:32:01 uebayasi Exp $	*/
 
 /*
  * Copyright (c) 1997 Charles D. Cranor and Washington University.
@@ -311,6 +311,9 @@
 
 int uvm_page_lookup_freelist(struct vm_page *);
 
+extern struct vm_page *uvm_page_zeropage;
+struct vm_page *uvm_page_zeropage_alloc(void);
+
 int vm_physseg_find(paddr_t, int *);
 struct vm_page *uvm_phys_to_vm_page(paddr_t);
 paddr_t uvm_vm_page_to_phys(const struct vm_page *);

Reply via email to