aboutsummaryrefslogtreecommitdiffstats
path: root/include/linux/mm.h
diff options
context:
space:
mode:
authorNick Piggin <npiggin@suse.de>2007-07-19 04:46:59 -0400
committerLinus Torvalds <torvalds@woody.linux-foundation.org>2007-07-19 13:04:41 -0400
commit54cb8821de07f2ffcd28c380ce9b93d5784b40d7 (patch)
tree1de676534963d96af42863b20191bc9f80060dea /include/linux/mm.h
parentd00806b183152af6d24f46f0c33f14162ca1262a (diff)
mm: merge populate and nopage into fault (fixes nonlinear)
Nonlinear mappings are (AFAIKS) simply a virtual memory concept that encodes the virtual address -> file offset differently from linear mappings. ->populate is a layering violation because the filesystem/pagecache code should need to know anything about the virtual memory mapping. The hitch here is that the ->nopage handler didn't pass down enough information (ie. pgoff). But it is more logical to pass pgoff rather than have the ->nopage function calculate it itself anyway (because that's a similar layering violation). Having the populate handler install the pte itself is likewise a nasty thing to be doing. This patch introduces a new fault handler that replaces ->nopage and ->populate and (later) ->nopfn. Most of the old mechanism is still in place so there is a lot of duplication and nice cleanups that can be removed if everyone switches over. The rationale for doing this in the first place is that nonlinear mappings are subject to the pagefault vs invalidate/truncate race too, and it seemed stupid to duplicate the synchronisation logic rather than just consolidate the two. After this patch, MAP_NONBLOCK no longer sets up ptes for pages present in pagecache. Seems like a fringe functionality anyway. NOPAGE_REFAULT is removed. This should be implemented with ->fault, and no users have hit mainline yet. [akpm@linux-foundation.org: cleanup] [randy.dunlap@oracle.com: doc. fixes for readahead] [akpm@linux-foundation.org: build fix] Signed-off-by: Nick Piggin <npiggin@suse.de> Signed-off-by: Randy Dunlap <randy.dunlap@oracle.com> Cc: Mark Fasheh <mark.fasheh@oracle.com> Signed-off-by: Andrew Morton <akpm@linux-foundation.org> Signed-off-by: Linus Torvalds <torvalds@linux-foundation.org>
Diffstat (limited to 'include/linux/mm.h')
-rw-r--r--include/linux/mm.h41
1 files changed, 34 insertions, 7 deletions
diff --git a/include/linux/mm.h b/include/linux/mm.h
index ca9536a348c8..f28a1b3e63a9 100644
--- a/include/linux/mm.h
+++ b/include/linux/mm.h
@@ -173,6 +173,7 @@ extern unsigned int kobjsize(const void *objp);
173 * In this case, do_no_page must 173 * In this case, do_no_page must
174 * return with the page locked. 174 * return with the page locked.
175 */ 175 */
176#define VM_CAN_NONLINEAR 0x10000000 /* Has ->fault & does nonlinear pages */
176 177
177#ifndef VM_STACK_DEFAULT_FLAGS /* arch can override this */ 178#ifndef VM_STACK_DEFAULT_FLAGS /* arch can override this */
178#define VM_STACK_DEFAULT_FLAGS VM_DATA_DEFAULT_FLAGS 179#define VM_STACK_DEFAULT_FLAGS VM_DATA_DEFAULT_FLAGS
@@ -196,6 +197,25 @@ extern unsigned int kobjsize(const void *objp);
196 */ 197 */
197extern pgprot_t protection_map[16]; 198extern pgprot_t protection_map[16];
198 199
200#define FAULT_FLAG_WRITE 0x01
201#define FAULT_FLAG_NONLINEAR 0x02
202
203/*
204 * fault_data is filled in the the pagefault handler and passed to the
205 * vma's ->fault function. That function is responsible for filling in
206 * 'type', which is the type of fault if a page is returned, or the type
207 * of error if NULL is returned.
208 *
209 * pgoff should be used in favour of address, if possible. If pgoff is
210 * used, one may set VM_CAN_NONLINEAR in the vma->vm_flags to get
211 * nonlinear mapping support.
212 */
213struct fault_data {
214 unsigned long address;
215 pgoff_t pgoff;
216 unsigned int flags;
217 int type;
218};
199 219
200/* 220/*
201 * These are the virtual MM functions - opening of an area, closing and 221 * These are the virtual MM functions - opening of an area, closing and
@@ -205,9 +225,15 @@ extern pgprot_t protection_map[16];
205struct vm_operations_struct { 225struct vm_operations_struct {
206 void (*open)(struct vm_area_struct * area); 226 void (*open)(struct vm_area_struct * area);
207 void (*close)(struct vm_area_struct * area); 227 void (*close)(struct vm_area_struct * area);
208 struct page * (*nopage)(struct vm_area_struct * area, unsigned long address, int *type); 228 struct page *(*fault)(struct vm_area_struct *vma,
209 unsigned long (*nopfn)(struct vm_area_struct * area, unsigned long address); 229 struct fault_data *fdata);
210 int (*populate)(struct vm_area_struct * area, unsigned long address, unsigned long len, pgprot_t prot, unsigned long pgoff, int nonblock); 230 struct page *(*nopage)(struct vm_area_struct *area,
231 unsigned long address, int *type);
232 unsigned long (*nopfn)(struct vm_area_struct *area,
233 unsigned long address);
234 int (*populate)(struct vm_area_struct *area, unsigned long address,
235 unsigned long len, pgprot_t prot, unsigned long pgoff,
236 int nonblock);
211 237
212 /* notification that a previously read-only page is about to become 238 /* notification that a previously read-only page is about to become
213 * writable, if an error is returned it will cause a SIGBUS */ 239 * writable, if an error is returned it will cause a SIGBUS */
@@ -661,7 +687,6 @@ static inline int page_mapped(struct page *page)
661 */ 687 */
662#define NOPAGE_SIGBUS (NULL) 688#define NOPAGE_SIGBUS (NULL)
663#define NOPAGE_OOM ((struct page *) (-1)) 689#define NOPAGE_OOM ((struct page *) (-1))
664#define NOPAGE_REFAULT ((struct page *) (-2)) /* Return to userspace, rerun */
665 690
666/* 691/*
667 * Error return values for the *_nopfn functions 692 * Error return values for the *_nopfn functions
@@ -1110,9 +1135,11 @@ extern void truncate_inode_pages_range(struct address_space *,
1110 loff_t lstart, loff_t lend); 1135 loff_t lstart, loff_t lend);
1111 1136
1112/* generic vm_area_ops exported for stackable file systems */ 1137/* generic vm_area_ops exported for stackable file systems */
1113extern struct page *filemap_nopage(struct vm_area_struct *, unsigned long, int *); 1138extern struct page *filemap_fault(struct vm_area_struct *, struct fault_data *);
1114extern int filemap_populate(struct vm_area_struct *, unsigned long, 1139extern struct page * __deprecated_for_modules
1115 unsigned long, pgprot_t, unsigned long, int); 1140filemap_nopage(struct vm_area_struct *, unsigned long, int *);
1141extern int __deprecated_for_modules filemap_populate(struct vm_area_struct *,
1142 unsigned long, unsigned long, pgprot_t, unsigned long, int);
1116 1143
1117/* mm/page-writeback.c */ 1144/* mm/page-writeback.c */
1118int write_one_page(struct page *page, int wait); 1145int write_one_page(struct page *page, int wait);