diff options
Diffstat (limited to 'fs')
-rw-r--r-- | fs/xfs/xfs_aops.c | 26 | ||||
-rw-r--r-- | fs/xfs/xfs_aops.h | 1 |
2 files changed, 10 insertions, 17 deletions
diff --git a/fs/xfs/xfs_aops.c b/fs/xfs/xfs_aops.c index d91564404abf..10660c364105 100644 --- a/fs/xfs/xfs_aops.c +++ b/fs/xfs/xfs_aops.c | |||
@@ -122,6 +122,11 @@ xfs_destroy_ioend( | |||
122 | bh->b_end_io(bh, !ioend->io_error); | 122 | bh->b_end_io(bh, !ioend->io_error); |
123 | } | 123 | } |
124 | 124 | ||
125 | if (ioend->io_iocb) { | ||
126 | if (ioend->io_isasync) | ||
127 | aio_complete(ioend->io_iocb, ioend->io_result, 0); | ||
128 | inode_dio_done(ioend->io_inode); | ||
129 | } | ||
125 | xfs_ioend_wake(ip); | 130 | xfs_ioend_wake(ip); |
126 | mempool_free(ioend, xfs_ioend_pool); | 131 | mempool_free(ioend, xfs_ioend_pool); |
127 | } | 132 | } |
@@ -236,8 +241,6 @@ xfs_end_io( | |||
236 | /* ensure we don't spin on blocked ioends */ | 241 | /* ensure we don't spin on blocked ioends */ |
237 | delay(1); | 242 | delay(1); |
238 | } else { | 243 | } else { |
239 | if (ioend->io_iocb) | ||
240 | aio_complete(ioend->io_iocb, ioend->io_result, 0); | ||
241 | xfs_destroy_ioend(ioend); | 244 | xfs_destroy_ioend(ioend); |
242 | } | 245 | } |
243 | } | 246 | } |
@@ -274,6 +277,7 @@ xfs_alloc_ioend( | |||
274 | * all the I/O from calling the completion routine too early. | 277 | * all the I/O from calling the completion routine too early. |
275 | */ | 278 | */ |
276 | atomic_set(&ioend->io_remaining, 1); | 279 | atomic_set(&ioend->io_remaining, 1); |
280 | ioend->io_isasync = 0; | ||
277 | ioend->io_error = 0; | 281 | ioend->io_error = 0; |
278 | ioend->io_list = NULL; | 282 | ioend->io_list = NULL; |
279 | ioend->io_type = type; | 283 | ioend->io_type = type; |
@@ -1289,7 +1293,6 @@ xfs_end_io_direct_write( | |||
1289 | bool is_async) | 1293 | bool is_async) |
1290 | { | 1294 | { |
1291 | struct xfs_ioend *ioend = iocb->private; | 1295 | struct xfs_ioend *ioend = iocb->private; |
1292 | struct inode *inode = ioend->io_inode; | ||
1293 | 1296 | ||
1294 | /* | 1297 | /* |
1295 | * blockdev_direct_IO can return an error even after the I/O | 1298 | * blockdev_direct_IO can return an error even after the I/O |
@@ -1300,28 +1303,17 @@ xfs_end_io_direct_write( | |||
1300 | 1303 | ||
1301 | ioend->io_offset = offset; | 1304 | ioend->io_offset = offset; |
1302 | ioend->io_size = size; | 1305 | ioend->io_size = size; |
1306 | ioend->io_iocb = iocb; | ||
1307 | ioend->io_result = ret; | ||
1303 | if (private && size > 0) | 1308 | if (private && size > 0) |
1304 | ioend->io_type = IO_UNWRITTEN; | 1309 | ioend->io_type = IO_UNWRITTEN; |
1305 | 1310 | ||
1306 | if (is_async) { | 1311 | if (is_async) { |
1307 | /* | 1312 | ioend->io_isasync = 1; |
1308 | * If we are converting an unwritten extent we need to delay | ||
1309 | * the AIO completion until after the unwrittent extent | ||
1310 | * conversion has completed, otherwise do it ASAP. | ||
1311 | */ | ||
1312 | if (ioend->io_type == IO_UNWRITTEN) { | ||
1313 | ioend->io_iocb = iocb; | ||
1314 | ioend->io_result = ret; | ||
1315 | } else { | ||
1316 | aio_complete(iocb, ret, 0); | ||
1317 | } | ||
1318 | xfs_finish_ioend(ioend); | 1313 | xfs_finish_ioend(ioend); |
1319 | } else { | 1314 | } else { |
1320 | xfs_finish_ioend_sync(ioend); | 1315 | xfs_finish_ioend_sync(ioend); |
1321 | } | 1316 | } |
1322 | |||
1323 | /* XXX: probably should move into the real I/O completion handler */ | ||
1324 | inode_dio_done(inode); | ||
1325 | } | 1317 | } |
1326 | 1318 | ||
1327 | STATIC ssize_t | 1319 | STATIC ssize_t |
diff --git a/fs/xfs/xfs_aops.h b/fs/xfs/xfs_aops.h index 71f721e1a71f..ce3dcb50762e 100644 --- a/fs/xfs/xfs_aops.h +++ b/fs/xfs/xfs_aops.h | |||
@@ -47,6 +47,7 @@ typedef struct xfs_ioend { | |||
47 | unsigned int io_type; /* delalloc / unwritten */ | 47 | unsigned int io_type; /* delalloc / unwritten */ |
48 | int io_error; /* I/O error code */ | 48 | int io_error; /* I/O error code */ |
49 | atomic_t io_remaining; /* hold count */ | 49 | atomic_t io_remaining; /* hold count */ |
50 | unsigned int io_isasync : 1; /* needs aio_complete */ | ||
50 | struct inode *io_inode; /* file being written to */ | 51 | struct inode *io_inode; /* file being written to */ |
51 | struct buffer_head *io_buffer_head;/* buffer linked list head */ | 52 | struct buffer_head *io_buffer_head;/* buffer linked list head */ |
52 | struct buffer_head *io_buffer_tail;/* buffer linked list tail */ | 53 | struct buffer_head *io_buffer_tail;/* buffer linked list tail */ |