diff options
Diffstat (limited to 'mm/filemap.c')
-rw-r--r-- | mm/filemap.c | 39 |
1 files changed, 20 insertions, 19 deletions
diff --git a/mm/filemap.c b/mm/filemap.c index c4fe97f5ace0..f6c1d22b504f 100644 --- a/mm/filemap.c +++ b/mm/filemap.c | |||
@@ -1226,12 +1226,11 @@ out: | |||
1226 | EXPORT_SYMBOL(__generic_file_aio_read); | 1226 | EXPORT_SYMBOL(__generic_file_aio_read); |
1227 | 1227 | ||
1228 | ssize_t | 1228 | ssize_t |
1229 | generic_file_aio_read(struct kiocb *iocb, char __user *buf, size_t count, loff_t pos) | 1229 | generic_file_aio_read(struct kiocb *iocb, const struct iovec *iov, |
1230 | unsigned long nr_segs, loff_t pos) | ||
1230 | { | 1231 | { |
1231 | struct iovec local_iov = { .iov_base = buf, .iov_len = count }; | ||
1232 | |||
1233 | BUG_ON(iocb->ki_pos != pos); | 1232 | BUG_ON(iocb->ki_pos != pos); |
1234 | return __generic_file_aio_read(iocb, &local_iov, 1, &iocb->ki_pos); | 1233 | return __generic_file_aio_read(iocb, iov, nr_segs, &iocb->ki_pos); |
1235 | } | 1234 | } |
1236 | EXPORT_SYMBOL(generic_file_aio_read); | 1235 | EXPORT_SYMBOL(generic_file_aio_read); |
1237 | 1236 | ||
@@ -2315,22 +2314,22 @@ out: | |||
2315 | current->backing_dev_info = NULL; | 2314 | current->backing_dev_info = NULL; |
2316 | return written ? written : err; | 2315 | return written ? written : err; |
2317 | } | 2316 | } |
2318 | EXPORT_SYMBOL(generic_file_aio_write_nolock); | ||
2319 | 2317 | ||
2320 | ssize_t | 2318 | ssize_t generic_file_aio_write_nolock(struct kiocb *iocb, |
2321 | generic_file_aio_write_nolock(struct kiocb *iocb, const struct iovec *iov, | 2319 | const struct iovec *iov, unsigned long nr_segs, loff_t pos) |
2322 | unsigned long nr_segs, loff_t *ppos) | ||
2323 | { | 2320 | { |
2324 | struct file *file = iocb->ki_filp; | 2321 | struct file *file = iocb->ki_filp; |
2325 | struct address_space *mapping = file->f_mapping; | 2322 | struct address_space *mapping = file->f_mapping; |
2326 | struct inode *inode = mapping->host; | 2323 | struct inode *inode = mapping->host; |
2327 | ssize_t ret; | 2324 | ssize_t ret; |
2328 | loff_t pos = *ppos; | ||
2329 | 2325 | ||
2330 | ret = __generic_file_aio_write_nolock(iocb, iov, nr_segs, ppos); | 2326 | BUG_ON(iocb->ki_pos != pos); |
2327 | |||
2328 | ret = __generic_file_aio_write_nolock(iocb, iov, nr_segs, | ||
2329 | &iocb->ki_pos); | ||
2331 | 2330 | ||
2332 | if (ret > 0 && ((file->f_flags & O_SYNC) || IS_SYNC(inode))) { | 2331 | if (ret > 0 && ((file->f_flags & O_SYNC) || IS_SYNC(inode))) { |
2333 | int err; | 2332 | ssize_t err; |
2334 | 2333 | ||
2335 | err = sync_page_range_nolock(inode, mapping, pos, ret); | 2334 | err = sync_page_range_nolock(inode, mapping, pos, ret); |
2336 | if (err < 0) | 2335 | if (err < 0) |
@@ -2338,6 +2337,7 @@ generic_file_aio_write_nolock(struct kiocb *iocb, const struct iovec *iov, | |||
2338 | } | 2337 | } |
2339 | return ret; | 2338 | return ret; |
2340 | } | 2339 | } |
2340 | EXPORT_SYMBOL(generic_file_aio_write_nolock); | ||
2341 | 2341 | ||
2342 | static ssize_t | 2342 | static ssize_t |
2343 | __generic_file_write_nolock(struct file *file, const struct iovec *iov, | 2343 | __generic_file_write_nolock(struct file *file, const struct iovec *iov, |
@@ -2347,8 +2347,9 @@ __generic_file_write_nolock(struct file *file, const struct iovec *iov, | |||
2347 | ssize_t ret; | 2347 | ssize_t ret; |
2348 | 2348 | ||
2349 | init_sync_kiocb(&kiocb, file); | 2349 | init_sync_kiocb(&kiocb, file); |
2350 | kiocb.ki_pos = *ppos; | ||
2350 | ret = __generic_file_aio_write_nolock(&kiocb, iov, nr_segs, ppos); | 2351 | ret = __generic_file_aio_write_nolock(&kiocb, iov, nr_segs, ppos); |
2351 | if (ret == -EIOCBQUEUED) | 2352 | if (-EIOCBQUEUED == ret) |
2352 | ret = wait_on_sync_kiocb(&kiocb); | 2353 | ret = wait_on_sync_kiocb(&kiocb); |
2353 | return ret; | 2354 | return ret; |
2354 | } | 2355 | } |
@@ -2361,28 +2362,28 @@ generic_file_write_nolock(struct file *file, const struct iovec *iov, | |||
2361 | ssize_t ret; | 2362 | ssize_t ret; |
2362 | 2363 | ||
2363 | init_sync_kiocb(&kiocb, file); | 2364 | init_sync_kiocb(&kiocb, file); |
2364 | ret = generic_file_aio_write_nolock(&kiocb, iov, nr_segs, ppos); | 2365 | kiocb.ki_pos = *ppos; |
2366 | ret = generic_file_aio_write_nolock(&kiocb, iov, nr_segs, *ppos); | ||
2365 | if (-EIOCBQUEUED == ret) | 2367 | if (-EIOCBQUEUED == ret) |
2366 | ret = wait_on_sync_kiocb(&kiocb); | 2368 | ret = wait_on_sync_kiocb(&kiocb); |
2369 | *ppos = kiocb.ki_pos; | ||
2367 | return ret; | 2370 | return ret; |
2368 | } | 2371 | } |
2369 | EXPORT_SYMBOL(generic_file_write_nolock); | 2372 | EXPORT_SYMBOL(generic_file_write_nolock); |
2370 | 2373 | ||
2371 | ssize_t generic_file_aio_write(struct kiocb *iocb, const char __user *buf, | 2374 | ssize_t generic_file_aio_write(struct kiocb *iocb, const struct iovec *iov, |
2372 | size_t count, loff_t pos) | 2375 | unsigned long nr_segs, loff_t pos) |
2373 | { | 2376 | { |
2374 | struct file *file = iocb->ki_filp; | 2377 | struct file *file = iocb->ki_filp; |
2375 | struct address_space *mapping = file->f_mapping; | 2378 | struct address_space *mapping = file->f_mapping; |
2376 | struct inode *inode = mapping->host; | 2379 | struct inode *inode = mapping->host; |
2377 | ssize_t ret; | 2380 | ssize_t ret; |
2378 | struct iovec local_iov = { .iov_base = (void __user *)buf, | ||
2379 | .iov_len = count }; | ||
2380 | 2381 | ||
2381 | BUG_ON(iocb->ki_pos != pos); | 2382 | BUG_ON(iocb->ki_pos != pos); |
2382 | 2383 | ||
2383 | mutex_lock(&inode->i_mutex); | 2384 | mutex_lock(&inode->i_mutex); |
2384 | ret = __generic_file_aio_write_nolock(iocb, &local_iov, 1, | 2385 | ret = __generic_file_aio_write_nolock(iocb, iov, nr_segs, |
2385 | &iocb->ki_pos); | 2386 | &iocb->ki_pos); |
2386 | mutex_unlock(&inode->i_mutex); | 2387 | mutex_unlock(&inode->i_mutex); |
2387 | 2388 | ||
2388 | if (ret > 0 && ((file->f_flags & O_SYNC) || IS_SYNC(inode))) { | 2389 | if (ret > 0 && ((file->f_flags & O_SYNC) || IS_SYNC(inode))) { |