Subject: Re: page loaning and pagedaemon
To: None <tech-kern@netbsd.org>
From: YAMAMOTO Takashi <yamt@mwd.biglobe.ne.jp>
List: tech-kern
Date: 12/06/2006 07:10:21
--NextPart-20061206065701-1836102
Content-Type: Text/Plain; charset=us-ascii

> hi,
> 
> currently ->K page loaning often removes pages from the page queue.
> because it confuses pagedaemon/pdpolicy much, i'd like to change it.
> ie. leave loaned pages on the page queue.
> 
> any comments?

here's a patch.

YAMAMOTO Takashi

--NextPart-20061206065701-1836102
Content-Type: Text/Plain; charset=us-ascii
Content-Disposition: attachment; filename="a.diff"

Index: miscfs/genfs/genfs_vnops.c
===================================================================
--- miscfs/genfs/genfs_vnops.c	(revision 1926)
+++ miscfs/genfs/genfs_vnops.c	(working copy)
@@ -1336,8 +1336,7 @@ genfs_putpages(void *v)
 				pg = tpg;
 			if (tpg->offset < startoff || tpg->offset >= endoff)
 				continue;
-			if (flags & PGO_DEACTIVATE && tpg->wire_count == 0
-			    && tpg->loan_count == 0) {
+			if (flags & PGO_DEACTIVATE && tpg->wire_count == 0) {
 				(void) pmap_clear_reference(tpg);
 				uvm_pagedeactivate(tpg);
 			} else if (flags & PGO_FREE) {
Index: uvm/uvm_aobj.c
===================================================================
--- uvm/uvm_aobj.c	(revision 1885)
+++ uvm/uvm_aobj.c	(working copy)
@@ -825,8 +825,8 @@ uao_put(struct uvm_object *uobj, voff_t 
 		case PGO_CLEANIT|PGO_DEACTIVATE:
 		case PGO_DEACTIVATE:
  deactivate_it:
-			/* skip the page if it's loaned or wired */
-			if (pg->loan_count != 0 || pg->wire_count != 0)
+			/* skip the page if it's wired */
+			if (pg->wire_count != 0)
 				continue;
 
 			/* ...and deactivate the page. */
Index: uvm/uvm_page.c
===================================================================
--- uvm/uvm_page.c	(revision 1799)
+++ uvm/uvm_page.c	(working copy)
@@ -1346,7 +1346,10 @@ uvm_pagefree(struct vm_page *pg)
 		pg->owner_tag = NULL;
 #endif
 		if (pg->loan_count) {
-			uvm_pagedequeue(pg);
+			KASSERT(pg->uobject == NULL);
+			if (pg->uanon == NULL) {
+				uvm_pagedequeue(pg);
+			}
 			return;
 		}
 	}
@@ -1508,12 +1511,12 @@ uvm_page_own(struct vm_page *pg, const c
 		    "page (%p)\n", pg);
 		panic("uvm_page_own");
 	}
-	KASSERT(uvmpdpol_pageisqueued_p(pg) ||
-	    (pg->uanon == NULL && pg->uobject == NULL) ||
-	    pg->uobject == uvm.kernel_object ||
-	    pg->wire_count > 0 ||
-	    (pg->loan_count == 1 && pg->uanon == NULL) ||
-	    pg->loan_count > 1);
+	if (!uvmpdpol_pageisqueued_p(pg)) {
+		KASSERT((pg->uanon == NULL && pg->uobject == NULL) ||
+		    pg->wire_count > 0);
+	} else {
+		KASSERT(pg->wire_count == 0);
+	}
 	pg->owner_tag = NULL;
 }
 #endif
Index: uvm/uvm_loan.c
===================================================================
--- uvm/uvm_loan.c	(revision 1885)
+++ uvm/uvm_loan.c	(working copy)
@@ -429,7 +429,6 @@ uvm_loananon(struct uvm_faultinfo *ufi, 
 		pmap_page_protect(pg, VM_PROT_READ);
 	}
 	pg->loan_count++;
-	uvm_pagedequeue(pg);
 	uvm_unlock_pageq();
 	**output = pg;
 	(*output)++;
@@ -479,7 +478,7 @@ uvm_loanpage(struct vm_page **pgpp, int 
 			pmap_page_protect(pg, VM_PROT_READ);
 		}
 		pg->loan_count++;
-		uvm_pagedequeue(pg);
+		uvm_pageactivate(pg);
 		uvm_unlock_pageq();
 	}
 
@@ -880,7 +879,6 @@ again:
 	if ((flags & UVM_LOAN_TOANON) == 0) {	/* loaning to kernel-page */
 		uvm_lock_pageq();
 		pg->loan_count++;
-		uvm_pagedequeue(pg);
 		uvm_unlock_pageq();
 		simple_unlock(&uvm_loanzero_object.vmobjlock);
 		**output = pg;
@@ -1011,16 +1009,10 @@ uvm_unloanpage(struct vm_page **ploans, 
 			pg->loan_count--;
 			pg->pqflags |= PQ_ANON;
 		}
-		if (pg->loan_count == 0) {
-			if (pg->uobject == NULL && pg->uanon == NULL) {
-				KASSERT((pg->flags & PG_BUSY) == 0);
-				uvm_pagefree(pg);
-			} else {
-				uvm_pageactivate(pg);
-			}
-		} else if (pg->loan_count == 1 && pg->uobject != NULL &&
-			   pg->uanon != NULL) {
-			uvm_pageactivate(pg);
+		if (pg->loan_count == 0 && pg->uobject == NULL &&
+		    pg->uanon == NULL) {
+			KASSERT((pg->flags & PG_BUSY) == 0);
+			uvm_pagefree(pg);
 		}
 		if (slock != NULL) {
 			simple_unlock(slock);
Index: uvm/uvm_fault.c
===================================================================
--- uvm/uvm_fault.c	(revision 1926)
+++ uvm/uvm_fault.c	(working copy)
@@ -200,7 +200,7 @@ uvmfault_anonflush(struct vm_anon **anon
 			continue;
 		simple_lock(&anons[lcv]->an_lock);
 		pg = anons[lcv]->an_page;
-		if (pg && (pg->flags & PG_BUSY) == 0 && pg->loan_count == 0) {
+		if (pg && (pg->flags & PG_BUSY) == 0) {
 			uvm_lock_pageq();
 			if (pg->wire_count == 0) {
 				pmap_clear_reference(pg);

--NextPart-20061206065701-1836102--