]> www.infradead.org Git - users/jedix/linux-maple.git/commitdiff
dio: add dio_lock_and_flush() helper
authorDave Kleikamp <dave.kleikamp@oracle.com>
Wed, 11 Jan 2012 21:25:26 +0000 (15:25 -0600)
committerDave Kleikamp <dave.kleikamp@oracle.com>
Fri, 13 Jan 2012 00:15:24 +0000 (18:15 -0600)
This creates a helper function which performs locking based on DIO_LOCKING
and flushes dirty pages.  This will be called by another entry point
like __blockdev_direct_IO() in an upcoming patch.

Signed-off-by: Zach Brown <zach.brown@oracle.com>
Signed-off-by: Dave Kleikamp <dave.kleikamp@oracle.com>
fs/direct-io.c

index 9462ed92371e7873302f24efa0e8e5d21f048796..ba4063e88fe962be4aade3263df4229822897908 100644 (file)
@@ -1118,6 +1118,35 @@ static void sdio_init(struct dio_submit *sdio, struct inode *inode,
                sdio->pages_in_io = 2;
 }
 
+static int dio_lock_and_flush(struct dio *dio, loff_t offset, loff_t end)
+{
+       struct inode *inode = dio->inode;
+       int ret;
+
+       if (dio->flags & DIO_LOCKING) {
+               /* watch out for a 0 len io from a tricksy fs */
+               if (dio->rw == READ && end > offset) {
+
+                       /* will be released by do_blockdev_direct_IO */
+                       mutex_lock(&inode->i_mutex);
+
+                       ret = filemap_write_and_wait_range(inode->i_mapping,
+                                                             offset, end - 1);
+                       if (ret) {
+                               mutex_unlock(&inode->i_mutex);
+                               return ret;
+                       }
+               }
+
+               /*
+                * Will be released at I/O completion, possibly in a
+                * different thread.
+                */
+               down_read_non_owner(&inode->i_alloc_sem);
+       }
+       return 0;
+}
+
 /*
  * This is a library function for use by filesystem drivers.
  *
@@ -1180,33 +1209,12 @@ do_blockdev_direct_IO(int rw, struct kiocb *iocb, struct inode *inode,
        if (!dio)
                goto out;
 
-       if (dio->flags & DIO_LOCKING) {
-               /* watch out for a 0 len io from a tricksy fs */
-               if (rw == READ && end > offset) {
-                       struct address_space *mapping =
-                                       iocb->ki_filp->f_mapping;
-
-                       /* will be released by direct_io_worker */
-                       mutex_lock(&inode->i_mutex);
-
-                       retval = filemap_write_and_wait_range(mapping, offset,
-                                                             end - 1);
-                       if (retval) {
-                               mutex_unlock(&inode->i_mutex);
-                               kmem_cache_free(dio_cache, dio);
-                               goto out;
-                       }
-               }
-
-               /*
-                * Will be released at I/O completion, possibly in a
-                * different thread.
-                */
-               down_read_non_owner(&inode->i_alloc_sem);
+       retval = dio_lock_and_flush(dio, offset, end);
+       if (retval) {   
+               kmem_cache_free(dio_cache, dio);
+               goto out;
        }
 
-       retval = 0;
-
        sdio_init(&sdio, inode, offset, blkbits, get_block, submit_io);
 
        for (seg = 0; seg < nr_segs; seg++) {