diff options
Diffstat (limited to 'mm/filemap_xip.c')
| -rw-r--r-- | mm/filemap_xip.c | 37 |
1 files changed, 14 insertions, 23 deletions
diff --git a/mm/filemap_xip.c b/mm/filemap_xip.c index 82f4b8e9834e..847d5d78163e 100644 --- a/mm/filemap_xip.c +++ b/mm/filemap_xip.c | |||
| @@ -210,8 +210,7 @@ __xip_unmap (struct address_space * mapping, | |||
| 210 | * | 210 | * |
| 211 | * This function is derived from filemap_fault, but used for execute in place | 211 | * This function is derived from filemap_fault, but used for execute in place |
| 212 | */ | 212 | */ |
| 213 | static struct page *xip_file_fault(struct vm_area_struct *area, | 213 | static int xip_file_fault(struct vm_area_struct *area, struct vm_fault *vmf) |
| 214 | struct fault_data *fdata) | ||
| 215 | { | 214 | { |
| 216 | struct file *file = area->vm_file; | 215 | struct file *file = area->vm_file; |
| 217 | struct address_space *mapping = file->f_mapping; | 216 | struct address_space *mapping = file->f_mapping; |
| @@ -222,19 +221,15 @@ static struct page *xip_file_fault(struct vm_area_struct *area, | |||
| 222 | /* XXX: are VM_FAULT_ codes OK? */ | 221 | /* XXX: are VM_FAULT_ codes OK? */ |
| 223 | 222 | ||
| 224 | size = (i_size_read(inode) + PAGE_CACHE_SIZE - 1) >> PAGE_CACHE_SHIFT; | 223 | size = (i_size_read(inode) + PAGE_CACHE_SIZE - 1) >> PAGE_CACHE_SHIFT; |
| 225 | if (fdata->pgoff >= size) { | 224 | if (vmf->pgoff >= size) |
| 226 | fdata->type = VM_FAULT_SIGBUS; | 225 | return VM_FAULT_SIGBUS; |
| 227 | return NULL; | ||
| 228 | } | ||
| 229 | 226 | ||
| 230 | page = mapping->a_ops->get_xip_page(mapping, | 227 | page = mapping->a_ops->get_xip_page(mapping, |
| 231 | fdata->pgoff*(PAGE_SIZE/512), 0); | 228 | vmf->pgoff*(PAGE_SIZE/512), 0); |
| 232 | if (!IS_ERR(page)) | 229 | if (!IS_ERR(page)) |
| 233 | goto out; | 230 | goto out; |
| 234 | if (PTR_ERR(page) != -ENODATA) { | 231 | if (PTR_ERR(page) != -ENODATA) |
| 235 | fdata->type = VM_FAULT_OOM; | 232 | return VM_FAULT_OOM; |
| 236 | return NULL; | ||
| 237 | } | ||
| 238 | 233 | ||
| 239 | /* sparse block */ | 234 | /* sparse block */ |
| 240 | if ((area->vm_flags & (VM_WRITE | VM_MAYWRITE)) && | 235 | if ((area->vm_flags & (VM_WRITE | VM_MAYWRITE)) && |
| @@ -242,26 +237,22 @@ static struct page *xip_file_fault(struct vm_area_struct *area, | |||
| 242 | (!(mapping->host->i_sb->s_flags & MS_RDONLY))) { | 237 | (!(mapping->host->i_sb->s_flags & MS_RDONLY))) { |
| 243 | /* maybe shared writable, allocate new block */ | 238 | /* maybe shared writable, allocate new block */ |
| 244 | page = mapping->a_ops->get_xip_page(mapping, | 239 | page = mapping->a_ops->get_xip_page(mapping, |
| 245 | fdata->pgoff*(PAGE_SIZE/512), 1); | 240 | vmf->pgoff*(PAGE_SIZE/512), 1); |
| 246 | if (IS_ERR(page)) { | 241 | if (IS_ERR(page)) |
| 247 | fdata->type = VM_FAULT_SIGBUS; | 242 | return VM_FAULT_SIGBUS; |
| 248 | return NULL; | ||
| 249 | } | ||
| 250 | /* unmap page at pgoff from all other vmas */ | 243 | /* unmap page at pgoff from all other vmas */ |
| 251 | __xip_unmap(mapping, fdata->pgoff); | 244 | __xip_unmap(mapping, vmf->pgoff); |
| 252 | } else { | 245 | } else { |
| 253 | /* not shared and writable, use xip_sparse_page() */ | 246 | /* not shared and writable, use xip_sparse_page() */ |
| 254 | page = xip_sparse_page(); | 247 | page = xip_sparse_page(); |
| 255 | if (!page) { | 248 | if (!page) |
| 256 | fdata->type = VM_FAULT_OOM; | 249 | return VM_FAULT_OOM; |
| 257 | return NULL; | ||
| 258 | } | ||
| 259 | } | 250 | } |
| 260 | 251 | ||
| 261 | out: | 252 | out: |
| 262 | fdata->type = VM_FAULT_MINOR; | ||
| 263 | page_cache_get(page); | 253 | page_cache_get(page); |
| 264 | return page; | 254 | vmf->page = page; |
| 255 | return VM_FAULT_MINOR; | ||
| 265 | } | 256 | } |
| 266 | 257 | ||
| 267 | static struct vm_operations_struct xip_file_vm_ops = { | 258 | static struct vm_operations_struct xip_file_vm_ops = { |
