Please note that diffs are not public domain; they are subject to the copyright notices on the relevant files. =================================================================== RCS file: /ftp/cvs/cvsroot/src/sys/uvm/uvm_page.h,v rcsdiff: /ftp/cvs/cvsroot/src/sys/uvm/uvm_page.h,v: warning: Unknown phrases like `commitid ...;' are present. retrieving revision 1.73 retrieving revision 1.73.2.9 diff -u -p -r1.73 -r1.73.2.9 --- src/sys/uvm/uvm_page.h 2011/06/12 03:36:03 1.73 +++ src/sys/uvm/uvm_page.h 2012/02/17 08:18:57 1.73.2.9 @@ -1,4 +1,4 @@ -/* $NetBSD: uvm_page.h,v 1.73 2011/06/12 03:36:03 rmind Exp $ */ +/* $NetBSD: uvm_page.h,v 1.73.2.9 2012/02/17 08:18:57 yamt Exp $ */ /* * Copyright (c) 1997 Charles D. Cranor and Washington University. @@ -79,10 +79,6 @@ * page, indexed by page number. Each structure * is an element of several lists: * - * A red-black tree rooted with the containing - * object is used to quickly perform object+ - * offset lookups - * * A list of all pages for a given object, * so they can be quickly deactivated at * time of deallocation. @@ -113,23 +109,22 @@ #include #include -#include - struct vm_page { - struct rb_node rb_node; /* tree of pages in obj (O) */ - union { TAILQ_ENTRY(vm_page) queue; LIST_ENTRY(vm_page) list; } pageq; /* queue info for FIFO * queue or free list (P) */ - union { - TAILQ_ENTRY(vm_page) queue; - LIST_ENTRY(vm_page) list; - } listq; /* pages in same object (O)*/ - struct vm_anon *uanon; /* anon (O,P) */ - struct uvm_object *uobject; /* object (O,P) */ + union { + struct { + struct vm_anon *o_anon; /* anon (O,P) */ + struct uvm_object *o_object; /* object (O,P) */ + } owner; +#define uanon u.owner.o_anon +#define uobject u.owner.o_object + LIST_ENTRY(vm_page) cpulist; + } u; voff_t offset; /* offset into object (O,P) */ uint16_t flags; /* object flags [O] */ uint16_t loan_count; /* number of active loans @@ -164,24 +159,33 @@ struct vm_page { * PG_ZERO is used to indicate that a page has been pre-zero'd. This flag * is only set when the page is on no queues, and is cleared when the page * is placed on the free list. + * + * PG_RDONLY is used to indicate that the page should not be mapped writably. + * typically they are set by pgo_get to inform the fault handler. + * + * if you want to renumber PG_CLEAN and PG_DIRTY, check __CTASSERTs in + * uvm_page_status.c first. */ -#define PG_BUSY 0x0001 /* page is locked */ -#define PG_WANTED 0x0002 /* someone is waiting for page */ -#define PG_TABLED 0x0004 /* page is in VP table */ -#define PG_CLEAN 0x0008 /* page has not been modified */ +#define PG_CLEAN 0x0001 /* page is known clean */ +#define PG_DIRTY 0x0002 /* page is known dirty */ +#define PG_BUSY 0x0004 /* page is locked */ +#define PG_WANTED 0x0008 /* someone is waiting for page */ #define PG_PAGEOUT 0x0010 /* page to be freed for pagedaemon */ #define PG_RELEASED 0x0020 /* page to be freed when unbusied */ #define PG_FAKE 0x0040 /* page is not yet initialized */ #define PG_RDONLY 0x0080 /* page must be mapped read-only */ #define PG_ZERO 0x0100 /* page is pre-zero'd */ -#define PG_MARKER 0x0200 /* dummy marker page */ +#define PG_TABLED 0x0200 /* page is in VP table */ #define PG_PAGER1 0x1000 /* pager-specific flag */ +#define PG_PAGER2 0x2000 /* pager-specific flag */ #define UVM_PGFLAGBITS \ - "\20\1BUSY\2WANTED\3TABLED\4CLEAN\5PAGEOUT\6RELEASED\7FAKE\10RDONLY" \ - "\11ZERO\12MARKER\15PAGER1" + "\20\1CLEAN\2DIRTY\3BUSY\4WANTED" \ + "\5PAGEOUT\6RELEASED\7FAKE\10RDONLY" \ + "\11ZERO\12TABLED" \ + "\15PAGER1\16PAGER2" #define PQ_FREE 0x0001 /* page is on free list */ #define PQ_ANON 0x0002 /* page is part of an anon, rather @@ -190,6 +194,8 @@ struct vm_page { uvm_object */ #define PQ_SWAPBACKED (PQ_ANON|PQ_AOBJ) #define PQ_READAHEAD 0x0008 /* read-ahead but has not been "hit" yet */ +#define PQ_FILE 0x0010 /* file backed (non-anonymous) */ +#define PQ_STAT (PQ_ANON|PQ_AOBJ|PQ_FILE) #define PQ_PRIVATE1 0x0100 #define PQ_PRIVATE2 0x0200 @@ -201,7 +207,7 @@ struct vm_page { #define PQ_PRIVATE8 0x8000 #define UVM_PQFLAGBITS \ - "\20\1FREE\2ANON\3AOBJ\4READAHEAD" \ + "\20\1FREE\2ANON\3AOBJ\4READAHEAD\5FILE" \ "\11PRIVATE1\12PRIVATE2\13PRIVATE3\14PRIVATE4" \ "\15PRIVATE5\16PRIVATE6\17PRIVATE7\20PRIVATE8" @@ -286,7 +292,33 @@ void uvm_pageunwire(struct vm_page *); void uvm_pagewire(struct vm_page *); void uvm_pagezero(struct vm_page *); bool uvm_pageismanaged(paddr_t); +unsigned int uvm_pagegetdirty(struct vm_page *); +void uvm_pagemarkdirty(struct vm_page *, unsigned int); +bool uvm_pagecheckdirty(struct vm_page *, bool); +bool uvm_pagereadonly_p(struct vm_page *); bool uvm_page_locked_p(struct vm_page *); +kmutex_t *uvm_page_getlock(struct vm_page *); +bool uvm_page_samelock_p(struct vm_page *, struct vm_page *); + +struct uvm_cpu; +struct uvm_cpu *uvm_cpu_get(void); +void uvm_cpu_put(struct uvm_cpu *); + +/* + * page dirtiness status for uvm_pagegetdirty and uvm_pagemarkdirty + * + * UNKNOWN means that we need to consult pmap to know if the page is + * dirty or not. + * basically, UVM_PAGE_STATUS_CLEAN implies that the page has no writable + * mapping. + * + * if you want to renumber these, check __CTASSERTs in + * uvm_page_status.c first. + */ +#define UVM_PAGE_STATUS_UNKNOWN 0 +#define UVM_PAGE_STATUS_CLEAN 1 +#define UVM_PAGE_STATUS_DIRTY 2 +#define UVM_PAGE_NUM_STATUS 3 int uvm_page_lookup_freelist(struct vm_page *); @@ -298,8 +330,6 @@ paddr_t uvm_vm_page_to_phys(const struct * macros */ -#define UVM_PAGE_TREE_PENALTY 4 /* XXX: a guess */ - #define VM_PAGE_TO_PHYS(entry) uvm_vm_page_to_phys(entry) #ifdef __HAVE_VM_PAGE_MD